nest new project-name
Нест работает через DI. Точка сборки — модуль, в нем должны быть объявлены все необходимые зависимости. controllers — роуты которые будут торчать наружу, imports — другие модули, которые необходимы для работы этого модуля, providers — это сервисы которые несту необходимо инстанцировать для работы модуля, по умолчанию они будут доступны только внутри модуля, пока не добавлены в exports, exports — провайдеры, которые должны быть доступны в других модулях при его импорте
Нест собирает их по принципу bottom-up. Контролерры обрабатывают все запросы приложения, можно определить неймспейс или указать конкретный путь у метода. Каждый сервис в nest.js — это Provider. По сути провайдер — это минимальная зависимость в терминах неста. В коде же это просто класс обернутый в Injectable. Самое важное это разделение ответвенности между контроллером и сервисом. Котроллер отвечает только за маппинг путей и параметров запроса, а вся бизнес-логика хранится в сервисе.
Parameter Properties — это сокращенный синтаксис присваивания аргументов констрктора свойсвам класса при использовании ключевых слов public
, private
, protected
Как происходит матчинг параметров. За это отвечает модуль reflect-metadata. Он позволяет в рантайме получить информацию о типах, включая параметры функций и конструкторов классов. Сами по себе провайдеры так же содержат токен инстанса когда импортируются. У всех провайдеров во время жизни приложения только один инстант — singleton.
providers: [CatsProvider]
// same
providers: [{provide: CatsProvider /* InjectionToken */, useClass: CatsProvider}]
npm install --save nestjs-pino pino-http pino-pretty
import { LoggerModule } from 'nestjs-pino';
// AppModule imports
LoggerModule.forRoot({
pinoHttp: {
transport: {
target: 'pino-pretty',
options: {
colorize: true
}
}
}
})
// main.ts
const app = await NestFactory.create(AppModule, { bufferLogs: true });
app.useLogger(app.get(Logger));
npm install --save joi
import Joi from 'joi';
import { ConfigModule, ConfigService } from '@nestjs/config';
// AppModule imports
ConfigModule.forRoot({
isGlobal: true,
envFilePath: ['.env.local', '.env'],
validationSchema: Joi.object({
NODE_ENV: Joi.string()
.valid('development', 'production', 'test', 'provision')
.default('development'),
PORT: Joi.number().default(3000),
DB_URL: Joi.string(),
}),
}),
npm install --save @nestjs/typeorm typeorm pg
import { TypeOrmModule } from '@nestjs/typeorm';
// AppModule imports
TypeOrmModule.forRootAsync({
imports: [ConfigModule],
useFactory: (configService: ConfigService) => ({
// name: 'default',
type: 'postgres',
url: configService.get<string>('DB_URL'),
extra: {
ssl: true,
rejectUnauthorized: false,
connectionLimit: 5,
},
autoLoadEntities: true,
synchronize: true,
logging: ['error'],
}),
inject: [ConfigService],
}),
npm install --save @nestjs/swagger
// nest-cli.json
"compilerOptions": {
"plugins": ["@nestjs/swagger"]
}
// main.ts
const app = await NestFactory.create(AppModule, {
cors: {
origin: true,
credentials: true,
},
bufferLogs: true,
});
// ...
const openApi = new DocumentBuilder()
.setTitle('project-name')
.build();
const swaggerOptions = {
persistAuthorization: true,
};
const options = { swaggerOptions };
const document = SwaggerModule.createDocument(app, openApi);
SwaggerModule.setup('/docs', app, document, options);