The main parts of an application
A NestJS application consists of four main parts, which together form the framework's architectural frame. Each plays its own role in building logically isolated yet interconnected layers.
1. Modules
A module is a container that groups related elements of the application: controllers, services, filters, pipes, and so on.
Every NestJS application always has at least one module - AppModule (the root one).
Example:
import { Module } from '@nestjs/common';
import { UsersModule } from './users/users.module';
import { AuthModule } from './auth/auth.module';
@Module({
imports: [UsersModule, AuthModule],
})
export class AppModule {}Role:
- defines the boundaries of a feature;
- encapsulates dependencies;
- provides scalability (new modules can be added without rewriting old ones).
2. Controllers
Controllers accept incoming requests (e.g. HTTP requests) and return responses to the client. They define the routes (endpoints) and hand execution off to services.
Example:
import { Controller, Get } from '@nestjs/common';
import { UsersService } from './users.service';
@Controller('users')
export class UsersController {
constructor(private readonly usersService: UsersService) {}
@Get()
findAll() {
return this.usersService.findAll();
}
}Role:
- the entry point for requests (HTTP, WebSocket, GraphQL, etc.);
- holds no business logic, just routing and passing data to services.
3. Providers
A provider is any entity that can be injected via Dependency Injection. The most common example is a service, which holds the business logic.
Example:
import { Injectable } from '@nestjs/common';
@Injectable()
export class UsersService {
private users = [{ id: 1, name: 'Alex' }];
findAll() {
return this.users;
}
}Role:
- implements the business logic;
- supplies data and functionality to other classes;
- managed by NestJS's DI container.
4. Decorators
Decorators are NestJS's key feature, letting you write declarative, readable code. They add metadata so Nest knows how to handle a class or method.
Examples of decorators:
| Decorator | Purpose |
|---|---|
@Module() | describes a module |
@Controller() | defines a controller |
@Injectable() | marks a class as a provider |
@Get(), @Post(), @Put() | define HTTP routes |
@Body(), @Param(), @Query() | extract data from the request |
@UseGuards(), @UseInterceptors() | attach middleware-like mechanisms |
Role:
- they simplify the architecture, making the code declarative and self-documenting.
How the components relate to each other
[ Client ]
↓
[ Controller ] → receives the request
↓
[ Service / Provider ] → handles the data and business logic
↓
[ Module ] → manages dependencies and assembles the components
↓
[ Response to the client ]Additional NestJS elements (supporting layers)
While the four main parts are the foundation, real applications often use other important components too:
| Component | Description |
|---|---|
| Pipes | Transform and validate input data |
| Guards | Control access (e.g. authorization) |
| Interceptors | Intercept requests/responses, add extra logic |
| Filters | Handle errors |
| Middlewares | Run before routing (e.g. logging) |
A typical application's overall structure
src/
├── app.module.ts
├── users/
│ ├── users.module.ts
│ ├── users.controller.ts
│ └── users.service.ts
├── auth/
│ ├── auth.module.ts
│ ├── auth.controller.ts
│ └── auth.service.ts
└── main.ts ← the entry point (bootstrapping the application)Summary
| Component | Purpose |
|---|---|
| Module | Groups and manages dependencies |
| Controller | Accepts requests and sends responses |
| Provider (Service) | Implements the business logic |
| Decorator | Defines components' behavior and structure |
Short Answer
Interview readyA concise answer to help you respond confidently on this topic during an interview.