Getting Started with NestJS: Your First API in TypeScript
Installing Nest, generating a CRUD resource, and understanding controllers, services, and DTO validation.
Modules, providers, and dependency injection are the three concepts that make NestJS feel different from plain Express — and once they click, the framework's structure stops feeling like ceremony and starts feeling like exactly the organization a growing API needs.
A module bundles controllers, providers, and related feature code into one cohesive unit. Every Nest app has at least a root AppModule, and every feature typically gets its own:
@Module({
controllers: [PostsController],
providers: [PostsService],
exports: [PostsService],
})
export class PostsModule {}
exports is what makes PostsService usable from OTHER modules that import PostsModule — without it, the service stays private to this module.
A provider is just a class Nest knows how to construct and hand to whoever asks for it — services, repositories, factories, even plain configuration objects. The @Injectable() decorator marks a class as available for injection:
@Injectable()
export class PostsService {
constructor(private prisma: PrismaService) {}
}
Instead of PostsService creating its own database connection with new PrismaService(), Nest's container creates ONE instance of PrismaService and hands the same instance to every class that asks for it. This has two huge practical benefits:
PrismaService instead of a real database connection, with zero changes to PostsService itself.By default every provider is a singleton — one instance for the entire application lifetime. You can opt into REQUEST scope for a provider that needs fresh state per incoming request, though this has a real performance cost and should be the exception, not the default.
@Module({
imports: [PostsModule, UsersModule],
})
export class AppModule {}
This is the whole system: modules group things, providers are the things, and dependency injection is how they find each other — without any class ever needing to know HOW to construct its own dependencies.
Installing Nest, generating a CRUD resource, and understanding controllers, services, and DTO validation.