import { Body, Controller, Get, Headers, Inject, Param, Post, Query, Req, Res, UseGuards, } from '@nestjs/common'; import { ApiBearerAuth, ApiTags } from '@nestjs/swagger'; import { z } from 'zod'; import { commissionImportRequestSchema, commissionImportPublishSchema, type Workspace, } from '@atlas/contracts'; import { CurrentWorkspace } from '../workspace/current-workspace.decorator.js'; import type { AuthenticatedRequest } from '../auth/auth.guard.js'; import { ApiError } from '../common/api-error.js'; import { SystemAdminGuard } from '../platform-catalog-admin/system-admin.guard.js'; import { CommissionImportService } from './commission-import.service.js'; function parse(schema: z.ZodType, value: unknown): T { const r = schema.safeParse(value); if (!r.success) throw new ApiError( 422, 'VALIDATION_ERROR', '请检查平台、版本名称、来源、采集日期及确认项', r.error.issues.map((i) => ({ field: i.path.join('.'), message: i.message, })), ); return r.data; } @ApiTags('System commissions') @ApiBearerAuth('access-token') @UseGuards(SystemAdminGuard) @Controller('system/pricing/commissions') export class CommissionImportController { constructor( @Inject(CommissionImportService) private readonly service: CommissionImportService, ) {} @Get() async list(@Query('platform_id') id: string) { return { data: await this.service.list(parse(z.uuid(), id)) }; } @Get(':id') async detail(@Param('id') id: string) { return { data: await this.service.detail(parse(z.uuid(), id)) }; } @Post('preview') async preview(@Body() body: unknown) { return { data: await this.service.preview( parse(commissionImportRequestSchema, body), ), }; } @Post('imports') async publish( @Body() body: unknown, @Req() req: AuthenticatedRequest, @CurrentWorkspace() w: Workspace, @Headers('idempotency-key') key: string | undefined, @Res({ passthrough: true }) res: { status: (n: number) => unknown }, ) { if (!key) throw new ApiError( 400, 'IDEMPOTENCY_KEY_REQUIRED', '需要 Idempotency-Key', ); const r = await this.service.publish( w.id, req.auth.userId, parse(z.uuid(), key), parse(commissionImportPublishSchema, body), ); res.status(r.status); return r.body; } }