简体   繁体   English

动态加载具有依赖关系的 Angular 组件

[英]Dynamically load Angular component with dependencies

I've been looking for a clean way (without using private API) solution to a widget style dashboard.我一直在为小部件样式仪表板寻找一种干净的方式(不使用私有 API)解决方案。 I want to dynamically load components onto it based on user role.我想根据用户角色动态地将组件加载到它上面。

Is there a way to import a component and dependencies that are included in components' module dynamically and is such solution production ready?有没有办法动态导入组件模块中包含的组件和依赖项,并且这种解决方案生产准备好了吗?

Stackblitz reproduction: Stackblitz 复制:

https://stackblitz.com/edit/angular-dynamically-loaded-dashboard?file=src/app/dashboard/dashboard.component.html https://stackblitz.com/edit/angular-dynamically-loaded-dashboard?file=src/app/dashboard/dashboard.component.html

Any help towards a clean solution is welcome.欢迎任何对清洁解决方案的帮助。

Edit: I have tried resolving components using ViewContainerRef, while the solution works (component is rendered), it just gets appended to the view, and I want to be able to get the reference of the component with resolved dependencies and pass it into a *ngComponentOutlet so I can use gridster to move and resize component.编辑:我尝试使用 ViewContainerRef 解析组件,虽然解决方案有效(组件被渲染),但它只是被附加到视图中,我希望能够获得具有已解决依赖项的组件的引用并将其传递给 * ngComponentOutlet 所以我可以使用 gridster 来移动和调整组件的大小。

I think what you are looking for is a ComponentFactoryResolver .我认为您正在寻找的是ComponentFactoryResolver Refer this demo code参考这个演示代码

  public render(): void {
    const index = Math.round(Math.random());
    const currentComponent = this.components[index];
    
    let componentFactory = this.componentFactoryResolver.resolveComponentFactory(currentComponent as any);

    let viewContainerRef = this.adHost.viewContainerRef;
    viewContainerRef.clear();

    let componentRef = viewContainerRef.createComponent(componentFactory);
  }

I've managed to solve it: The missing link was the ngModuleFactory part:我已经设法解决它:缺少的链接是 ngModuleFactory 部分:

  <ng-container
    *ngComponentOutlet="widget.component; ngModuleFactory: widget.module"
  ></ng-container>

And in widget.service.ts I've resolved the module:在 widget.service.ts 我已经解决了模块:

   const { TasksWidgetModule } = await import('../tasks-widget/tasks-widget.module');
   module = await this.compiler.compileModuleAsync(TasksWidgetModule);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM