Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Pass Implementation to Angular Module When importing it

If I have an Angular Module A that depends on a certain service S. But instead of implementing the service directly, I want to deal with an interface I and let the consumer of A pass the actual implementation when importing it. The implementation will be an Angular service decorated with @Injectable and has its own dependencies.

Is that feasible in Angular? if yes, what are the steps to implement it?

like image 630
meno Avatar asked Jun 24 '26 12:06

meno


1 Answers

To archive this, you could use abstract classes instead of interfaces to make the implementations exchangeable:

app/
├── foo.service.ts
├── foo/
│   ├── abstract-foo.provider.ts
│   ├── foo.module.ts
│   ├── foo.component.ts
├── app.module.ts

Now the following files:

// foo.service.ts
@Injectable()
export class FooService extends AbstractFooProvider {
   ctor(private _fooDependency: SomeOtherFooService){}
   foo(): boolean {
     return this._fooDependency.isFoo();
   }
}

// foo.module.ts
@NgModule({
  declarations: [FooComponent],
  exports: [FooComponent]
})
export class FooModule {
   static withConfiguration(implementationProvider: Provider): ModuleWithProviders {
     return {
        ngModule: FooModule,
        providers: [implementationProvider]
     };
   }
}

// abstract-foo.provider.ts
export abstract class AbstractFooProvider {
    foo(): boolean;
}

// foo.component.ts
@Component({})
export class FooComponent {
   ctor(private _fooProvider: AbstractFooProvider){}
}

// app.module.ts    

export const FOO_PROVIDER : ClassProvider = {
  provide: AbstractFooProvider, 
  useClass: FooService
};

@NgModule({
   imports: [
      FooModule.withConfiguration(FOO_PROVIDER)
   ]
})
export class AppModule {}
like image 130
Jota.Toledo Avatar answered Jun 26 '26 04:06

Jota.Toledo