我会利用Angular Lazy加载功能模块来实现可插入的前端
所以这个概念是在我的应用程序中创建扩展点,在那里我可以做这样的事情:
import('./customers/customers.component').then(lazyMod => {
here use lazyMod.CustomersComponent to plug other component's template
})
我在stackblitz中的一个简单PoC中开发了这个想法:
https://angular-9-dynamic-lazy-test.stackblitz.io
情况1-OK-按下PoC的按钮1,运行以下代码,即可:
const { HelloComponent } = await import('./hello.component')
情况2-OK-按下PoC的按钮1(bis(,运行以下代码,即可:
const helloLazyModulePath = './hello.component'; //component already loaded in case 1
const { HelloComponent } = await import(helloLazyModulePath );
情况3-KO-按下PoC的按钮2,它运行以下代码,我得到错误:
const goodbyeLazyModulePath = './goodbye.component';
const { GoodbyeComponent } = await import(goodbyeLazyModulePath);
错误为:Uncaught (in promise): Error: Cannot find module
生成警告显示:Critical dependency: the request of a dependency is an expression
原因应该是:
根据https://angular.io/guide/deployment#lazy-加载
The CLI runs the Angular Ahead-of-Time Webpack Plugin which automatically recognizes
lazy-loaded NgModules and creates separate bundles for them
这意味着webpackangular工具在构建阶段扫描源代码以找出@import('path')
,并为懒惰模块创建一个单独的捆绑包
因此,如果@import
通常使用@import(variable)
,则webpack无法确定哪个功能模块必须构建在单独的捆绑包中。
我需要使用@import(variable)
,因为我知道只有在构建阶段才能导入哪个插件模块,这取决于许多因素,例如我将在哪个环境中部署。
有没有一种方法(解决方法或编译设置(可以使用@import(variable)
,而不会在运行时因丢失分离的捆绑包而出错?
EDIT:除了stackblitz,我在这个github repo 中推送了相同的PoC
路径的动态性如何?我的意思是,你应该能够知道所有可能的路径。所以你可以做一些类似的事情:
let componentToUse: Component;
switch (dynamicArg) {
case 'a':
componentToUse = (await import('path/to/a')).ComponentA;
break;
...
}