Как загрузить файл удаленной конфигурации для лениво загруженного модуля в Angular - PullRequest
1 голос
/ 15 апреля 2020

У меня есть Angular (v6) SPA с несколькими лениво загруженными модулями. В настоящее время у меня есть json файл, содержащий конфигурацию для приложения, которую можно изменить через отдельный интерфейс администратора, не требуя перестройки / развертывания приложения. Файл конфигурации в настоящее время загружен в APP_INITIALIZER, который хорошо работает, чтобы гарантировать, что я получу конфигурацию, прежде чем позволить приложению полностью bootstrap.

Я хочу разделить этот файл конфигурации на модуль, имея одну общую конфигурацию загружается в APP_INITIALIZER и загружает остальные только тогда, когда этот конкретный модуль загружается с отложенной загрузкой.

Есть ли принятый или рекомендуемый способ сделать это? Кажется, я ничего не могу найти в angular документах или вообще в net. Одним из подходов может быть выбор конфигурации в конструкторе модулей, но, насколько я вижу, у меня нет способа предотвратить продолжение загрузки модуля и установки всех его компонентов и т. Д. c до тех пор, пока не будет получен этот файл конфигурации. и где-то хранится.

Может ли преобразователь маршрута служить этой цели, если я установлю его на маршруте root для лениво загруженного модуля? Например, вместо того, чтобы возвращать какие-либо данные, я мог бы внедрить некоторый «ConfigService» в распознаватель, который получит соответствующий файл конфигурации и сохранит его, а затем разрешит преобразователь.

Тогда компоненты в этом модуле могут внедрить это тот же ConfigService, получающий доступ к любым точкам конфигурации, которые были получены.

1 Ответ

2 голосов
/ 15 апреля 2020

Выбор конфигурации во время инициализации модуля (в конструкторе или в методе stati c, таком как forRoot) не будет работать, так как на этом этапе зависимости не были разрешены. Так, например, у вас не будет HttpClient доступных для извлечения данных.

Что может быть приемлемым способом:

1. Укажите ConfigurationService, который получает введенный URL-адрес вашего файла конфигурации

@Injectable()
export class ConfigService {

  private config$ = new BehaviorSubject<any | null>(null);
  private loadedConfig = false;

  constructor(@Inject(CONFIG_URL) private configUrl: string,
              private httpClient: HttpClient) {
    this.getConfig();
  }

  getConfig(): Observable<any> {
    if (!this.loadedConfig) {
      this.loadedConfig = true;
      this.httpClient.get(this.configUrl).subscribe(this.config$);
    }
    return this.config$;
  }

}

2. Предоставьте ConfigurationService как часть модуля, который может динамически устанавливать CONFIG_URL:

@NgModule({
  providers: [ConfigService],
  imports: [
    HttpClientModule
  ]
})
export class ConfigModule {
  static buildForConfigUrl(configUrl: string): ModuleWithProviders {
    return {
      ngModule: ConfigModule,
      providers: [
        {
          provide: CONFIG_URL,
          useValue: configUrl
        }
      ]
    };
  }
}

3. Импортируйте ConfigModule в свои функциональные модули

Теперь, когда у вас есть функциональный модуль, который должен иметь собственную конфигурацию, просто импортируйте ConfigModule, используя buildForConfigUrl:

@NgModule({
  exports: [
    MyComponent
  ],
  declarations: [
    MyComponent
  ],
  imports: [
    ConfigModule.buildForConfigUrl('https://my-url/my-config.json')
  ]
})
export class FeatureModule {
}

4. Используйте ConfigService в своих компонентах:

@Component({
  selector: 'my-component',
  template: 'I am your new component. My config is: {{ config$ | async | json }}'
})
export class MyComponent implements OnInit{

  config$: Observable<any>;

  constructor(private configService: ConfigService) {
  }

  ngOnInit(): void {
    this.config$ = this.configService.getConfig();
  }

}

При таком подходе вы прекрасно отделили проблемы: ваши функциональные модули не должны заботиться о том, как загружается конфигурация, но все же ее компоненты имеют конфигурация доступна во время выполнения.

Если вы хотите сделать go на один шаг дальше, вы даже можете удалить определение URL-адресов конфигурации из ваших функциональных модулей и переместить его в AppModule централизованно.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...