Files
rent/apps/server/src/modules/merchant/merchant.service.ts
T
2026-04-24 18:17:21 +08:00

137 lines
3.7 KiB
TypeScript

import {
Injectable,
NotFoundException,
BadRequestException,
} from '@nestjs/common';
import { InjectRepository } from '@nestjs/typeorm';
import { Repository } from 'typeorm';
import { Merchant } from '@/entities/merchant.entity';
import {
ApplyMerchantDto,
UpdateMerchantDto,
QueryMerchantDto,
} from './dto/merchant.dto';
@Injectable()
export class MerchantService {
constructor(
@InjectRepository(Merchant)
private merchantRepo: Repository<Merchant>,
) {}
async apply(sellerId: number, dto: ApplyMerchantDto) {
const existing = await this.merchantRepo.findOne({ where: { sellerId } });
if (existing) {
throw new BadRequestException('您已提交过商家申请');
}
const merchant = this.merchantRepo.create({ sellerId, ...dto });
return this.merchantRepo.save(merchant);
}
async findBySellerId(sellerId: number) {
return this.merchantRepo.findOne({ where: { sellerId } });
}
async findById(id: number) {
const merchant = await this.merchantRepo.findOne({ where: { id } });
if (!merchant) throw new NotFoundException('商家不存在');
return merchant;
}
async update(id: number, dto: UpdateMerchantDto) {
const merchant = await this.findById(id);
// 审核通过或审核拒绝后修改信息,需要重新进入审核
if (merchant.status === 'approved' || merchant.status === 'rejected') {
await this.merchantRepo.update(id, {
...dto,
status: 'pending',
rejectReason: '',
});
} else {
await this.merchantRepo.update(id, dto);
}
return this.findById(id);
}
async findPublic(query: QueryMerchantDto) {
const { page = 1, pageSize = 10, keyword, city } = query;
const safePage = Number(page) || 1;
const safePageSize = Number(pageSize) || 10;
const qb = this.merchantRepo
.createQueryBuilder('m')
.where('m.status = :status', { status: 'approved' });
if (keyword) {
qb.andWhere('m.shop_name LIKE :kw', { kw: `%${keyword}%` });
}
if (city) {
qb.andWhere('m.city = :city', { city });
}
qb.orderBy('m.rating', 'DESC');
qb.skip((safePage - 1) * safePageSize).take(safePageSize);
const [list, total] = await qb.getManyAndCount();
return {
list,
total,
page: safePage,
pageSize: safePageSize,
totalPages: Math.ceil(total / safePageSize),
};
}
async findAll(query: QueryMerchantDto) {
const { page = 1, pageSize = 10, keyword, status, city } = query;
const qb = this.merchantRepo.createQueryBuilder('m');
if (keyword) {
qb.andWhere('(m.shop_name LIKE :kw OR m.phone LIKE :kw)', {
kw: `%${keyword}%`,
});
}
if (status) {
qb.andWhere('m.status = :status', { status });
}
if (city) {
qb.andWhere('m.city = :city', { city });
}
qb.orderBy('m.createdAt', 'DESC');
qb.skip((page - 1) * pageSize).take(pageSize);
const [list, total] = await qb.getManyAndCount();
return {
list,
total,
page,
pageSize,
totalPages: Math.ceil(total / pageSize),
};
}
async approve(id: number) {
await this.merchantRepo.update(id, { status: 'approved' });
return { message: '商家已通过审核' };
}
async reject(id: number, reason: string) {
await this.merchantRepo.update(id, {
status: 'rejected',
rejectReason: reason,
});
return { message: '商家已拒绝' };
}
async freeze(id: number) {
await this.merchantRepo.update(id, { status: 'frozen' });
return { message: '店铺已冻结' };
}
async unfreeze(id: number) {
await this.merchantRepo.update(id, { status: 'approved' });
return { message: '店铺已解冻' };
}
}