diff --git a/app/assets/javascripts/discourse/app/widgets/render-glimmer.js b/app/assets/javascripts/discourse/app/widgets/render-glimmer.js
index 3adc020614..ce96a1a585 100644
--- a/app/assets/javascripts/discourse/app/widgets/render-glimmer.js
+++ b/app/assets/javascripts/discourse/app/widgets/render-glimmer.js
@@ -70,6 +70,16 @@ export default class RenderGlimmer {
}
update(prev) {
+ if (
+ prev.template.__id !== this.template.__id ||
+ prev.tagName !== this.tagName
+ ) {
+ // Totally different component, but the widget framework guessed it was the
+ // same widget. Destroy old component and re-init the new one.
+ prev.destroy();
+ return this.init();
+ }
+
this._componentInfo = prev._componentInfo;
if (prev.data !== this.data) {
this._componentInfo.data = this.data;
diff --git a/app/assets/javascripts/discourse/tests/integration/components/widgets/render-glimmer-test.js b/app/assets/javascripts/discourse/tests/integration/components/widgets/render-glimmer-test.js
index edbe15d97a..db86f08864 100644
--- a/app/assets/javascripts/discourse/tests/integration/components/widgets/render-glimmer-test.js
+++ b/app/assets/javascripts/discourse/tests/integration/components/widgets/render-glimmer-test.js
@@ -66,6 +66,41 @@ class DemoComponent extends ClassicComponent {
}
}
+class ToggleDemoWidget extends Widget {
+ static actionTriggered = false;
+ tagName = "div.my-widget";
+
+ buildKey() {
+ return "abc";
+ }
+
+ defaultState() {
+ return {
+ showOne: true,
+ };
+ }
+
+ html(attrs, state) {
+ const output = [
+ this.attach("button", {
+ label: "toggle",
+ className: "toggleButton",
+ action: "toggleComponent",
+ }),
+ ];
+ if (state.showOne) {
+ output.push(new RenderGlimmer(this, "div.glimmer-wrapper", hbs`One`, {}));
+ } else {
+ output.push(new RenderGlimmer(this, "div.glimmer-wrapper", hbs`Two`, {}));
+ }
+ return output;
+ }
+
+ toggleComponent() {
+ this.state.showOne = !this.state.showOne;
+ }
+}
+
module("Integration | Component | Widget | render-glimmer", function (hooks) {
setupRenderingTest(hooks);
@@ -73,11 +108,13 @@ module("Integration | Component | Widget | render-glimmer", function (hooks) {
DemoComponent.eventLog = [];
DemoWidget.actionTriggered = false;
this.registry.register("widget:demo-widget", DemoWidget);
+ this.registry.register("widget:toggle-demo-widget", ToggleDemoWidget);
this.registry.register("component:demo-component", DemoComponent);
});
hooks.afterEach(function () {
this.registry.unregister("widget:demo-widget");
+ this.registry.unregister("widget:toggle-demo-widget");
this.registry.unregister("component:demo-component");
});
@@ -217,4 +254,13 @@ module("Integration | Component | Widget | render-glimmer", function (hooks) {
new RenderGlimmer(this, "div", hbs``);
assert.true(true, "it doesn't raise an error for correct params");
});
+
+ test("multiple adjacent components", async function (assert) {
+ await render(hbs``);
+ assert.strictEqual(query("div.glimmer-wrapper").innerText, "One");
+ await click(".toggleButton");
+ assert.strictEqual(query("div.glimmer-wrapper").innerText, "Two");
+ await click(".toggleButton");
+ assert.strictEqual(query("div.glimmer-wrapper").innerText, "One");
+ });
});