diff --git a/CHANGELOG.md b/CHANGELOG.md
index c2977ed988..c2c84ef8cb 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -42,6 +42,12 @@ Our versioning strategy is as follows:
* Upgrade to Node.js 20.x ([#1679](https://github.com/Sitecore/jss/pull/1679))([#1681](https://github.com/Sitecore/jss/pull/1681))
* `[nextjs/template]` Upgrade graphql-codegen packages to latest ([#1711](https://github.com/Sitecore/jss/pull/1711))
+## 21.6.3
+
+### 🐛 Bug Fixes
+
+* `[sitecore-jss-angular]` Missing ngModuleRef in lazy loaded components ([#1743](https://github.com/Sitecore/jss/pull/1743))
+
## 21.6.2
### 🐛 Bug Fixes
diff --git a/packages/sitecore-jss-angular/src/components/placeholder.component.spec.ts b/packages/sitecore-jss-angular/src/components/placeholder.component.spec.ts
index 7da7590941..787641e22e 100644
--- a/packages/sitecore-jss-angular/src/components/placeholder.component.spec.ts
+++ b/packages/sitecore-jss-angular/src/components/placeholder.component.spec.ts
@@ -11,6 +11,7 @@ import {
convertedDevData as nonEeDevData,
convertedLayoutServiceData as nonEeLsData,
} from '../test-data/non-ee-data';
+import { LazyComponent } from '../test-data/lazy-component.component';
@Component({
selector: 'test-placeholder',
@@ -69,11 +70,22 @@ describe('', () => {
],
imports: [
RouterTestingModule,
- JssModule.withComponents([
- { name: 'DownloadCallout', type: TestDownloadCalloutComponent },
- { name: 'Home', type: TestHomeComponent },
- { name: 'Jumbotron', type: TestJumbotronComponent },
- ]),
+ JssModule.withComponents(
+ [
+ { name: 'DownloadCallout', type: TestDownloadCalloutComponent },
+ { name: 'Home', type: TestHomeComponent },
+ { name: 'Jumbotron', type: TestJumbotronComponent },
+ ],
+ [
+ {
+ path: 'LazyComponent',
+ loadChildren: () =>
+ import('../test-data/lazy-loading.module').then(
+ (m) => m.AngularLazyLoadingModule
+ ),
+ },
+ ]
+ ),
],
providers: [],
}).compileComponents();
@@ -123,6 +135,10 @@ describe('', () => {
expect(downloadCallout).not.toBeNull();
expect(downloadCallout.nativeElement.innerHTML).toContain('Download');
+ const lazyComponent = de.query(By.directive(LazyComponent));
+ expect(lazyComponent).not.toBeNull();
+ expect(lazyComponent.nativeElement.innerHTML).toContain('Push');
+
const img = de.nativeElement.getElementsByTagName('img')[0];
expect(img).not.toBeDefined();
})
diff --git a/packages/sitecore-jss-angular/src/components/placeholder.component.ts b/packages/sitecore-jss-angular/src/components/placeholder.component.ts
index 70e3c10e5c..e55118804e 100644
--- a/packages/sitecore-jss-angular/src/components/placeholder.component.ts
+++ b/packages/sitecore-jss-angular/src/components/placeholder.component.ts
@@ -307,6 +307,7 @@ export class PlaceholderComponent implements OnInit, OnChanges, DoCheck, OnDestr
// work-around for https://github.com/angular/angular/issues/12215
const createdComponentRef = this.view.createComponent(rendering.componentImplementation, {
index: index,
+ ngModuleRef: rendering.componentModuleRef,
});
if (this.parentStyleAttribute) {
this.renderer.setAttribute(
diff --git a/packages/sitecore-jss-angular/src/services/jss-component-factory.service.ts b/packages/sitecore-jss-angular/src/services/jss-component-factory.service.ts
index c08c9e7402..943b9e2762 100644
--- a/packages/sitecore-jss-angular/src/services/jss-component-factory.service.ts
+++ b/packages/sitecore-jss-angular/src/services/jss-component-factory.service.ts
@@ -1,4 +1,4 @@
-import { Inject, Injectable, Injector, Type, createNgModule } from '@angular/core';
+import { createNgModule, Inject, Injectable, Injector, NgModuleRef, Type } from '@angular/core';
import { ComponentRendering, HtmlElementRendering } from '@sitecore-jss/sitecore-jss/layout';
import {
ComponentNameAndModule,
@@ -17,6 +17,7 @@ export interface ComponentFactoryResult {
// eslint-disable-next-line @typescript-eslint/no-explicit-any
componentImplementation?: Type;
componentDefinition: ComponentRendering | HtmlElementRendering;
+ componentModuleRef?: NgModuleRef;
canActivate?:
| JssCanActivate
| Type
@@ -86,6 +87,7 @@ export class JssComponentFactoryService {
return {
componentDefinition: component,
componentImplementation: componentType,
+ componentModuleRef: moduleRef,
canActivate: lazyComponent.canActivate,
resolve: lazyComponent.resolve,
};
diff --git a/packages/sitecore-jss-angular/src/test-data/ee-data.ts b/packages/sitecore-jss-angular/src/test-data/ee-data.ts
index 00672f6057..740158c0de 100644
--- a/packages/sitecore-jss-angular/src/test-data/ee-data.ts
+++ b/packages/sitecore-jss-angular/src/test-data/ee-data.ts
@@ -199,6 +199,60 @@ export const convertedData = {
class: 'scpm',
},
},
+
+ {
+ name: 'code',
+ type: 'text/sitecore',
+ contents:
+ '{"commands":[{"click":"chrome:rendering:sort","header":"Change position","icon":"/temp/iconcache/office/16x16/document_size.png","disabledIcon":"/temp/document_size_disabled16x16.png","isDivider":false,"tooltip":"Move component.","type":""},{"click":"javascript:Sitecore.PageModes.PageEditor.postRequest(\'webedit:componentoptions(referenceId={6701AC71-845D-4DE4-BF8E-1F4FEDDF8908},renderingId={6C254609-5347-4768-9FFB-1FF620320CE9},id={199C8794-311F-4B50-9BDC-88AEFB3EE172})\',null,false)","header":"Edit Experience Editor Options","icon":"/temp/iconcache/office/16x16/clipboard_check_edit.png","disabledIcon":"/temp/clipboard_check_edit_disabled16x16.png","isDivider":false,"tooltip":"Edit the Experience Editor options for the component.","type":"common"},{"click":"chrome:rendering:properties","header":"Edit component properties","icon":"/temp/iconcache/office/16x16/elements_branch.png","disabledIcon":"/temp/elements_branch_disabled16x16.png","isDivider":false,"tooltip":"Edit the properties for the component.","type":"common"},{"click":"javascript:Sitecore.PageModes.PageEditor.postRequest(\'webedit:setdatasource(referenceId={6701AC71-845D-4DE4-BF8E-1F4FEDDF8908},renderingId={6C254609-5347-4768-9FFB-1FF620320CE9},id={199C8794-311F-4B50-9BDC-88AEFB3EE172})\',null,false)","header":"{dsHeader}","icon":"/temp/iconcache/office/16x16/data.png","disabledIcon":"/temp/data_disabled16x16.png","isDivider":false,"tooltip":"{dsTooltip}","type":"datasourcesmenu"},{"click":"chrome:rendering:personalize({command:\\"webedit:personalize\\"})","header":"Personalize","icon":"/temp/iconcache/office/16x16/users_family.png","disabledIcon":"/temp/users_family_disabled16x16.png","isDivider":false,"tooltip":"Create or edit personalization for this component.","type":"sticky"},{"click":"chrome:rendering:editvariations({command:\\"webedit:editvariations\\"})","header":"Edit variations","icon":"/temp/iconcache/office/16x16/windows.png","disabledIcon":"/temp/windows_disabled16x16.png","isDivider":false,"tooltip":"Test the component.","type":"sticky"},{"click":"chrome:common:edititem({command:\\"webedit:open\\"})","header":"Edit the related item","icon":"/temp/iconcache/office/16x16/cubes.png","disabledIcon":"/temp/cubes_disabled16x16.png","isDivider":false,"tooltip":"Edit the related item in the Content Editor.","type":"datasourcesmenu"},{"click":"chrome:rendering:delete","header":"Delete","icon":"/temp/iconcache/office/16x16/delete.png","disabledIcon":"/temp/delete_disabled16x16.png","isDivider":false,"tooltip":"Remove component.","type":"sticky"}],"contextItemUri":"sitecore://master/{199C8794-311F-4B50-9BDC-88AEFB3EE172}?lang=en&ver=1","custom":{"renderingID":"6C254609534747689FFB1FF620320CE9","editable":"true"},"displayName":"DownloadCalloutRendering","expandedDisplayName":null}',
+ attributes: {
+ type: 'text/sitecore',
+ chrometype: 'rendering',
+ kind: 'open',
+ hintname: 'LazyComponentRendering',
+ id: 'r_6701AC71845D4DE4BF8E1F4FEDDF8908',
+ class: 'scpm',
+ 'data-selectable': 'true',
+ },
+ },
+ {
+ uid: '6701ac71-845d-4de4-bf8e-1f4feddf8908',
+ componentName: 'LazyComponent',
+ fields: {
+ linkText: {
+ value: 'Push',
+ editable:
+ '{"commands":[{"click":"chrome:common:edititem({command:\\"webedit:open\\"})","header":"Edit the related item","icon":"/temp/iconcache/office/16x16/cubes.png","disabledIcon":"/temp/cubes_disabled16x16.png","isDivider":false,"tooltip":"Edit the related item in the Content Editor.","type":"common"},{"click":"chrome:rendering:personalize({command:\\"webedit:personalize\\"})","header":"Personalize","icon":"/temp/iconcache/office/16x16/users_family.png","disabledIcon":"/temp/users_family_disabled16x16.png","isDivider":false,"tooltip":"Create or edit personalization for this component.","type":"sticky"},{"click":"chrome:rendering:editvariations({command:\\"webedit:editvariations\\"})","header":"Edit variations","icon":"/temp/iconcache/office/16x16/windows.png","disabledIcon":"/temp/windows_disabled16x16.png","isDivider":false,"tooltip":"Edit the variations.","type":"sticky"}],"contextItemUri":"sitecore://master/{199C8794-311F-4B50-9BDC-88AEFB3EE172}?lang=en&ver=1","custom":{},"displayName":"LinkText","expandedDisplayName":null}Push',
+ },
+ },
+ params: {},
+ },
+ {
+ name: 'div',
+ type: '',
+ contents:
+ '',
+ attributes: {
+ style: {
+ backgroundColor: 'white',
+ opacity: 0.35,
+ filter: 'alpha(opacity=35)',
+ },
+ },
+ },
+ {
+ name: 'code',
+ type: 'text/sitecore',
+ contents: '',
+ attributes: {
+ type: 'text/sitecore',
+ id: 'scEnclosingTag_r_',
+ chrometype: 'rendering',
+ kind: 'close',
+ hintkey: 'LazyComponentRendering',
+ class: 'scpm',
+ },
+ },
{
name: 'code',
type: 'text/sitecore',
diff --git a/packages/sitecore-jss-angular/src/test-data/lazy-component.component.ts b/packages/sitecore-jss-angular/src/test-data/lazy-component.component.ts
new file mode 100644
index 0000000000..f755bd07ea
--- /dev/null
+++ b/packages/sitecore-jss-angular/src/test-data/lazy-component.component.ts
@@ -0,0 +1,20 @@
+import { ComponentRendering } from '@sitecore-jss/sitecore-jss/layout';
+import { MockService } from './mock.service';
+import { Component, Input } from '@angular/core';
+
+@Component({
+ selector: 'lazy-component',
+ template: `
+ {{ rendering?.fields?.linkText?.value }}
+ {{ getNum() }}
+ `,
+})
+export class LazyComponent {
+ @Input() rendering: ComponentRendering;
+
+ constructor(private mockService: MockService) {}
+
+ getNum() {
+ return this.mockService.get(10);
+ }
+}
diff --git a/packages/sitecore-jss-angular/src/test-data/lazy-loading.module.ts b/packages/sitecore-jss-angular/src/test-data/lazy-loading.module.ts
new file mode 100644
index 0000000000..26ef6be458
--- /dev/null
+++ b/packages/sitecore-jss-angular/src/test-data/lazy-loading.module.ts
@@ -0,0 +1,11 @@
+import { NgModule } from '@angular/core';
+import { MockService } from './mock.service';
+import { LazyComponent } from './lazy-component.component';
+import { JssModule } from '../lib.module';
+
+@NgModule({
+ imports: [JssModule.forChild(LazyComponent)],
+ declarations: [LazyComponent],
+ providers: [MockService],
+})
+export class AngularLazyLoadingModule {}
diff --git a/packages/sitecore-jss-angular/src/test-data/mock.service.ts b/packages/sitecore-jss-angular/src/test-data/mock.service.ts
new file mode 100644
index 0000000000..6ff7575c95
--- /dev/null
+++ b/packages/sitecore-jss-angular/src/test-data/mock.service.ts
@@ -0,0 +1,8 @@
+import { Injectable } from '@angular/core';
+
+@Injectable()
+export class MockService {
+ get(num: number): number {
+ return num;
+ }
+}
diff --git a/packages/sitecore-jss-angular/src/test-data/non-ee-data.ts b/packages/sitecore-jss-angular/src/test-data/non-ee-data.ts
index 774df55b4a..863289f818 100644
--- a/packages/sitecore-jss-angular/src/test-data/non-ee-data.ts
+++ b/packages/sitecore-jss-angular/src/test-data/non-ee-data.ts
@@ -51,6 +51,16 @@ export const convertedDevData = {
uid: '6701ac71-845d-4de4-bf8e-1f4feddf8908',
params: [],
},
+ {
+ componentName: 'LazyComponent',
+ fields: {
+ linkText: {
+ value: 'Push',
+ },
+ },
+ uid: '6701ac71-845d-4de4-bf8e-1f4feddf8908',
+ params: [],
+ },
],
},
},
@@ -125,6 +135,17 @@ export const convertedLayoutServiceData = {
uid: '6701ac71-845d-4de4-bf8e-1f4feddf8908',
params: [],
},
+ {
+ componentName: 'LazyComponent',
+ fields: {
+ linkText: {
+ value: 'Push',
+ editable: 'Push',
+ },
+ },
+ uid: '6701ac71-845d-4de4-bf8e-1f4feddf8908',
+ params: [],
+ },
],
},
},