feat(api): add inquiries, leads, and agents modules for Agent Portal
Build three new DDD modules following existing CQRS patterns: - Inquiries: CRUD endpoints for buyer consultation requests with agent notification support - Leads: Full lead lifecycle management with status state machine and conversion tracking - Agents: Quality score calculation (event-driven on review changes) and dashboard stats API All modules include unit tests (14 test files, all 797 tests pass). Co-Authored-By: Paperclip <noreply@paperclip.ing>
This commit is contained in:
@@ -0,0 +1,61 @@
|
||||
import { Controller, Get, Param, Post, UseGuards } from '@nestjs/common';
|
||||
import { type CommandBus, type QueryBus } from '@nestjs/cqrs';
|
||||
import {
|
||||
ApiBearerAuth,
|
||||
ApiOperation,
|
||||
ApiParam,
|
||||
ApiResponse,
|
||||
ApiTags,
|
||||
} from '@nestjs/swagger';
|
||||
import {
|
||||
type JwtPayload,
|
||||
CurrentUser,
|
||||
JwtAuthGuard,
|
||||
RolesGuard,
|
||||
Roles,
|
||||
} from '@modules/auth';
|
||||
import { RecalculateQualityScoreCommand } from '../../application/commands/recalculate-quality-score/recalculate-quality-score.command';
|
||||
import { GetAgentDashboardQuery } from '../../application/queries/get-agent-dashboard/get-agent-dashboard.query';
|
||||
import type { AgentDashboardData } from '../../domain/repositories/agent.repository';
|
||||
|
||||
@ApiTags('agents')
|
||||
@Controller('agents')
|
||||
export class AgentsController {
|
||||
constructor(
|
||||
private readonly commandBus: CommandBus,
|
||||
private readonly queryBus: QueryBus,
|
||||
) {}
|
||||
|
||||
@ApiBearerAuth('JWT')
|
||||
@ApiOperation({ summary: 'Get agent dashboard stats' })
|
||||
@ApiResponse({ status: 200, description: 'Agent dashboard data' })
|
||||
@ApiResponse({ status: 401, description: 'Unauthorized' })
|
||||
@ApiResponse({ status: 403, description: 'Forbidden — only agents' })
|
||||
@ApiResponse({ status: 404, description: 'Agent profile not found' })
|
||||
@UseGuards(JwtAuthGuard, RolesGuard)
|
||||
@Roles('AGENT')
|
||||
@Get('me/dashboard')
|
||||
async getDashboard(
|
||||
@CurrentUser() user: JwtPayload,
|
||||
): Promise<AgentDashboardData> {
|
||||
return this.queryBus.execute(new GetAgentDashboardQuery(user.sub));
|
||||
}
|
||||
|
||||
@ApiBearerAuth('JWT')
|
||||
@ApiOperation({ summary: 'Recalculate quality score (admin/system)' })
|
||||
@ApiParam({ name: 'agentId', description: 'Agent ID' })
|
||||
@ApiResponse({ status: 201, description: 'Quality score recalculated' })
|
||||
@ApiResponse({ status: 401, description: 'Unauthorized' })
|
||||
@ApiResponse({ status: 403, description: 'Forbidden — only admins' })
|
||||
@UseGuards(JwtAuthGuard, RolesGuard)
|
||||
@Roles('ADMIN')
|
||||
@Post(':agentId/recalculate-score')
|
||||
async recalculateScore(
|
||||
@Param('agentId') agentId: string,
|
||||
): Promise<{ message: string }> {
|
||||
await this.commandBus.execute(
|
||||
new RecalculateQualityScoreCommand(agentId),
|
||||
);
|
||||
return { message: 'Quality score recalculated' };
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user