Inject model into service
Use the
@injectModel()
decorator and pass in the schema name.Model<schema class name>
is a fixed notation. Same here as express, but also write async/await to make Promises easier to manage and more readable.Enter
this.coffeeModel.
here to see all available methods. Compared to mongoose in express,this.coffeeModel
here is equivalent to the originalSchema name (capitalized)
, such asStore
,Category
,User
, etc.
In the service file:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46import { Injectable, NotFoundException } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { Model } from 'mongoose';
import { Coffee } from './entities/coffee.entity';
()
export class CoffeesService {
constructor(
private readonly coffeeModel: Model<Coffee>, (Coffee.name)
){}
async findAll(){
return this.coffeeModel.find().exec();
};
async findOne(id: string){
const coffee = await this.coffeeModel.findOne({ _id: id}).exec();
if(!coffee) {
throw new NotFoundException(`Coffee #${id} not found`);
}
return coffee;
};
async create(createCoffeeDto: CreateCoffeeDto){ //Type verification
const coffee = new this.coffeeModel( createCoffeeDto );
return coffee.save();
};
async create(createCoffeeDto: CreateCoffeeDto){ //Another way of writing
const coffee = await this.coffeeModel.create( createCoffeeDto );
return coffee;
};
async update(id: string, updateCoffeeDto: UpdateCoffeeDto){
const existingCoffee = await this.coffeeModel.findByIdAndUpdate({ _id: id }, { $set: updateCoffeeDto }, { new: true }).exec();
if(!exsitingCoffee){
throw new NotFoundException(`Coffee #${id} not found`);
}
return coffee;
}
async remove(id: string){
const coffee = await this.findOne(id);
return coffee.remove();
}
}$set: Update a field in the document instead of replacing it all.
In remove , there is no need to remove the manual validation
(!coffee)
, as findOne will automatically return an error when it cannot find the target.
Changes in Controller file
First id should be changed from number to string. This is because in mongoDB
_id
is a string and not a number. If this is not changed, the ValidationPipe will try to automatically convert the “id” of any incoming object to a number, resulting in a lot of random errors.
Pagination
First create pagination:
nest g class common/dto/pagination-query.dto --no-spec
. The pagination is created with a new class name in order to hold things that are not tied to any specific field and can be reused by multiple controllers.In the pagination-query.dto file:
1
2
3
4
5
6
7
8
9
10
11
12
13import { Type } from 'class-transformer';
export class PaginationQueryDto {
()
()
() => Number) //This can be removed by global setting implicit conversion (
limit: number;
()
()
() => Number) //This can be removed by global setting implicit conversion (
offset: number;
}
In main.ts file:
1
2
3
4
5
6
7
8
9
10
11
12
13async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.useGlobalPipes(
new ValidationPipe({
whitelist: true,
transform: true,
forbidNonwhitelisted: true,
transformOptions: {
enableImplicitConversion: true, //Set this item
}
})
)
}
In the controller file:
1
2
3
4
5
6
7
8
9()
export class CoffeesService {
constructor(
private readonly coffeeModel: Model<Coffee>, (Coffee.name)
){}
async findAll(){ () paginationQuery: PaginationQueryDto
return this.coffeeModel.findAll(paginationQuery).exec();
};
In the service file:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16import { Injectable, NotFoundException } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { Model } from 'mongoose';
import { Coffee } from './entities/coffee.entity';
()
export class CoffeesService {
constructor(
private readonly coffeeModel: Model<Coffee>, (Coffee.name)
){}
async findAll(paginationQuery: PaginationDto){
const {limit, offset} = paginationQuery;
return this.coffeeModel.find().skip(offset).limit(limit)exec();
};
}
Sort syntax
1
2
3
4Post.find({}).sort('test').exec(function(err, docs) { ... });
Post.find({}).sort([['date', -1]]).exec(function(err, docs) { ... });
Post.find({}).sort({test: 1}).exec(function(err, docs) { ... });
Post.find({}, null, {sort: {date: 1}}, function(err, docs) { ... });