Search code examples
angulartypescriptangular-componentsangular-module

Angular 2 'component' is not a known element


I'm trying to use a component I created inside the AppModule in other modules. I get the following error though:

"Uncaught (in promise): Error: Template parse errors:

'contacts-box' is not a known element:

  1. If 'contacts-box' is an Angular component, then verify that it is part of this module.
  2. If 'contacts-box' is a Web Component then add 'CUSTOM_ELEMENTS_SCHEMA' to the '@NgModule.schemas' of this component to suppress this message.

My project structure is quite simple: Overall project structure

I keep my pages in pages directory, where each page is kept in different module (e.g. customers-module) and each module has multiple components (like customers-list-component, customers-add-component and so on). I want to use my ContactBoxComponent inside those components (so inside customers-add-component for example).

As you can see I created the contacts-box component inside the widgets directory so it's basically inside the AppModule. I added the ContactBoxComponent import to app.module.ts and put it in declarations list of AppModule. It didin't work so I googled my problem and added ContactBoxComponent to export list as well. Didn't help. I also tried putting ContactBoxComponent in CustomersAddComponent and then in another one (from different module) but I got an error saying there are multiple declarations.

What am I missing?


Solution

  • These are the 5 steps I perform when I get such an error.

    • Are you sure the name is correct? (Also check the selector defined in the component)
    • Declare the component in a module?
    • If it is in another module, export the component?
    • If it is in another module, import that module?
    • Restart the cli?

    When the error occurs during unit testing, make sure your declared the component or imported the module in TestBed.configureTestingModule

    I also tried putting ContactBoxComponent in CustomersAddComponent and then in another one (from different module) but I got an error saying there are multiple declarations.

    You can't declare a component twice. You should declare and export your component in a new separate module. Next, you should import this new module in every module you want to use your component.

    It is hard to tell when you should create a new module and when you shouldn't. I usually create a new module for every component I reuse. When I have some components that I use almost everywhere I put them in a single module. When I have a component that I don't reuse I won't create a separate module until I need it somewhere else.

    Though it might be tempting to put all your components in a single module, this is bad for the performance. While developing, a module has to recompile every time changes are made. The bigger the module (more components) the more time it takes. Making a small change to a big module takes more time than making a small change in a small module.

    EDIT for v15

    Angular 15 introduced so-called 'Standalone' components. These components DO NOT need to be declared in a module.

    @Component({
      selector: 'app-hello',
      standalone: true, <------ NOTE THIS
      template: 'hello world',
    })
    export class StandaloneComponent {}
    

    Using a standalone component in a module component:

    @NgModule({
      imports: [
        CommonModule,
        StandaloneComponent
      ],
      declarations: [ModuleComponent],
      exports: [ModuleComponent],
    })
    export class ExampleModule {}
    

    Using a module component in a standalone component:

    @Component({
      selector: 'app-hello',
      standalone: true,
      template: 'hello world <module-component></module-component>',
      imports: [ExampleModule]
    })
    export class StandaloneComponent {}