feat(CC-061): add PATCH /ai-requests/:id/status and status filter on list endpoint
This commit is contained in:
parent
fe1bdbbbe0
commit
c5d256ea78
1 changed files with 37 additions and 2 deletions
|
|
@ -1,20 +1,30 @@
|
|||
import { Controller, Get, NotFoundException, Param, ParseUUIDPipe, Query } from '@nestjs/common';
|
||||
import { Body, Controller, Get, IsString, NotFoundException, Param, ParseUUIDPipe, Patch, Post, Query } from '@nestjs/common';
|
||||
import { and, desc, eq, sum, count } from 'drizzle-orm';
|
||||
import { IsIn, IsOptional } from 'class-validator';
|
||||
import { CurrentSession } from '../auth/session.decorator';
|
||||
import type { AuthenticatedSession } from '../auth/tenant.guard';
|
||||
import { db } from '../db/client';
|
||||
import { aiRequests } from '../db/schema';
|
||||
|
||||
class UpdateAiRequestStatusDto {
|
||||
@IsIn(['completed', 'cancelled']) resultStatus!: 'completed' | 'cancelled';
|
||||
@IsOptional() @IsString() rejectionReason?: string;
|
||||
}
|
||||
|
||||
@Controller('ai-requests')
|
||||
export class AiRequestsController {
|
||||
@Get()
|
||||
async list(
|
||||
@CurrentSession() session: AuthenticatedSession,
|
||||
@Query('limit') limitStr?: string,
|
||||
@Query('status') status?: string,
|
||||
) {
|
||||
const limit = Math.min(Math.max(1, parseInt(limitStr ?? '200', 10) || 200), 500);
|
||||
const where = status
|
||||
? and(eq(aiRequests.tenantId, session.tenantId), eq(aiRequests.resultStatus, status))
|
||||
: eq(aiRequests.tenantId, session.tenantId);
|
||||
return db.query.aiRequests.findMany({
|
||||
where: eq(aiRequests.tenantId, session.tenantId),
|
||||
where,
|
||||
orderBy: desc(aiRequests.createdAt),
|
||||
limit,
|
||||
columns: {
|
||||
|
|
@ -86,4 +96,29 @@ export class AiRequestsController {
|
|||
}
|
||||
return record;
|
||||
}
|
||||
|
||||
@Patch(':id/status')
|
||||
async updateStatus(
|
||||
@CurrentSession() session: AuthenticatedSession,
|
||||
@Param('id', ParseUUIDPipe) id: string,
|
||||
@Body() dto: UpdateAiRequestStatusDto,
|
||||
) {
|
||||
const record = await db.query.aiRequests.findFirst({
|
||||
where: and(
|
||||
eq(aiRequests.id, id),
|
||||
eq(aiRequests.tenantId, session.tenantId),
|
||||
),
|
||||
columns: { id: true, resultStatus: true },
|
||||
});
|
||||
if (!record) throw new NotFoundException('AI request not found');
|
||||
if (record.resultStatus !== 'pending') {
|
||||
return { updated: false, reason: 'request is not pending' };
|
||||
}
|
||||
const [updated] = await db
|
||||
.update(aiRequests)
|
||||
.set({ resultStatus: dto.resultStatus, completedAt: new Date() })
|
||||
.where(eq(aiRequests.id, id))
|
||||
.returning({ id: aiRequests.id, resultStatus: aiRequests.resultStatus, completedAt: aiRequests.completedAt });
|
||||
return { updated: true, record: updated };
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue