angularangular-router-loader

Angular4. How to declare components/import modules for lazy loaded submodules?


For now for each rout of my app I am loading exact module. Here is how I am doing that :

const routes: Routes = [
    {
        path: '',
        loadChildren: './pages/site-index/site-index-routing.module#SiteIndexRoutingModule'
    }
    {
        path: 'account',
        loadChildren: './pages/site-account/site-account-routing.module#SiteAccountRoutingModule'
    }
];

If I declare the following components : HeaderComponent, MenuComponent, FooterComponent in app.module.ts like that :

const BASE_COMPONENTS: any[] = [
    HeaderComponent,
    FooterComponent,
    MenuComponent
];



@NgModule({
    imports: [
        BrowserModule,
        AppRoutingModule
    ],
    declarations: [
        AppComponent,
        ...BASE_COMPONENTS
    ],
    bootstrap: [ AppComponent ]
})

But!

If I declare HeaderComponent, FooterComponent, MenuComponent both in SiteIndexModule and SiteAccountModule - these cry that HeaderComponent, FooterComponent, MenuComponent were declared in two places and ask to declare in any module above containing SiteIndexModule and SiteAccountModule

P.S. If I declare HeaderComponent, FooterComponent, MenuComponent only in SiteIndexModule and do not use these by SiteAccountModule - everything is ok. The problem is only when I'd like to use HeaderComponent, FooterComponent, MenuComponent in several lazy-loaded modules.

How can I resolve my problem?

thanks


Solution

  • The best way to do something like this where you are using the same components in several modules, is to use a shared module and import it into the sub-modules you need to use the components in.

    The Angular Docs do a pretty good job of explaining how it works. There are also TONS of resources regarding the use of 'Shared' modules online. I will say that if you get into the habit of sharing singelton services, it's worth your time to research exactly how services work, espeically within the context of lazy loaded modules.

    This gist though is that you have a /shared folder in your root app directory with a shared.module.ts module in it, along with all of the components, directives, services, etc.. you want to share. The trick here is that along with importing them into the shared.module.ts, you also export them out so other modules that use the shared module gain access to them. Then when you want to use any of those within a module, you import the shared module.

    src/app/src/app/shared/shared.module.ts

    import { NgModule }            from '@angular/core';
    import { CommonModule }        from '@angular/common';
    import { FormsModule }         from '@angular/forms';
    
    import { FooterComponent }  from './PATH-TO-FILE';
    import { HeaderComponent }  from './PATH-TO-FILE';
    import { MenuCompoonent } from './PATH-TO-FILE';
    
    @NgModule({
      imports:      [ CommonModule ],
      declarations: [ HeaderComponent, FooterComponent, MenuComponent ],
      exports:      [ HeaderComponent, FooterComponent, MenuComponent
                      CommonModule, FormsModule ]
    })
    export class SharedModule { }