0
0
NestJSframework~5 mins

Async configuration in NestJS

Choose your learning style9 modes available
Introduction

Async configuration lets you set up your app using data that might come from slow sources like databases or remote servers. This helps your app start only after it has all the needed settings.

When you need to load configuration from a database before the app starts.
When fetching secrets or API keys from a remote vault service asynchronously.
When configuration depends on environment variables that require async processing.
When you want to delay configuration until some async initialization completes.
Syntax
NestJS
ConfigModule.forRootAsync({
  imports: [OtherModule],
  useFactory: async (dependency) => ({
    key: await dependency.getValue(),
  }),
  inject: [Dependency],
  isGlobal: true,
})

useFactory is an async function that returns the config object.

inject lists dependencies to pass into the factory function.

Examples
Loads config asynchronously without dependencies.
NestJS
ConfigModule.forRootAsync({
  useFactory: async () => ({
    databaseHost: await getHostFromRemote(),
  }),
})
Loads config using a service from another module.
NestJS
ConfigModule.forRootAsync({
  imports: [SecretsModule],
  useFactory: async (secretsService) => ({
    apiKey: await secretsService.getApiKey(),
  }),
  inject: [SecretsService],
})
Sample Program

This example shows how to load configuration asynchronously from a service that simulates fetching data remotely. The app waits for the config before starting.

NestJS
import { Module } from '@nestjs/common';
import { ConfigModule, ConfigService } from '@nestjs/config';
import { NestFactory } from '@nestjs/core';

class RemoteConfigService {
  async getConfig() {
    // Simulate async config fetch
    return new Promise(resolve => setTimeout(() => resolve({ port: 3000 }), 100));
  }
}

@Module({
  providers: [RemoteConfigService],
  exports: [RemoteConfigService],
})
class RemoteConfigModule {}

@Module({
  imports: [
    RemoteConfigModule,
    ConfigModule.forRootAsync({
      imports: [RemoteConfigModule],
      useFactory: async (remoteConfigService: RemoteConfigService) => {
        const config = await remoteConfigService.getConfig();
        return {
          port: config.port,
        };
      },
      inject: [RemoteConfigService],
      isGlobal: true,
    }),
  ],
})
export class AppModule {}

// Usage example
async function bootstrap() {
  const app = await NestFactory.create(AppModule);
  const configService = app.get(ConfigService);
  console.log('Port:', configService.get('port'));
  await app.close();
}

bootstrap();
OutputSuccess
Important Notes

Async config helps when config values are not immediately available.

Always inject needed services in inject array to use them in useFactory.

Set isGlobal: true to make config available everywhere without importing repeatedly.

Summary

Async configuration loads settings that need time or external calls.

Use forRootAsync with useFactory and inject to set it up.

This ensures your app starts with all config ready.