import { Controller, Get, Param, Patch, Post, Body, UseGuards } from '@nestjs/common';
import { ApiTags, ApiOperation, ApiBearerAuth, ApiBody } from '@nestjs/swagger';
import { NotificationsService } from './notifications.service';
import { JwtGuard } from '../../common/jwt.guard';
import { PassengerStaff } from '../../common/passenger-guards';
import { PASSENGER_PERMS } from '../../seed/passenger-permissions.registry';
import { TestNotificationDto, CreateTemplateDto, UpdateTemplateDto } from './notifications.dto';
import { EmailClientService } from './email-client.service';
import { SmsClientService } from './sms-client.service';
import { SendEmail } from './dtos/email.dto';
import { BulkMessagesDto, SingleMessageDto } from './dtos/sms.dto';

@ApiTags('Notifications')
@Controller('notifications')
@UseGuards(JwtGuard)
@ApiBearerAuth('JWT-auth')
export class NotificationsController {
  constructor(
    private service: NotificationsService,
    private emailClient: EmailClientService,
    private smsClient: SmsClientService,
  ) {}

  // --- Template management (declared before the ':passengerId' catch-all so the
  // static 'templates' segment isn't captured as a passenger id) ---

  @Get('templates')
  @PassengerStaff([PASSENGER_PERMS.notifications.send, PASSENGER_PERMS.admin])
  @ApiOperation({ summary: 'List notification templates' })
  listTemplates() {
    return this.service.listTemplates();
  }

  @Get('templates/:id')
  @PassengerStaff([PASSENGER_PERMS.notifications.send, PASSENGER_PERMS.admin])
  @ApiOperation({ summary: 'Get a notification template' })
  getTemplate(@Param('id') id: string) {
    return this.service.getTemplate(id);
  }

  @Post('templates')
  @PassengerStaff([PASSENGER_PERMS.notifications.send, PASSENGER_PERMS.admin])
  @ApiOperation({ summary: 'Create a notification template' })
  @ApiBody({ type: CreateTemplateDto })
  createTemplate(@Body() dto: CreateTemplateDto) {
    return this.service.createTemplate(dto);
  }

  @Patch('templates/:id')
  @PassengerStaff([PASSENGER_PERMS.notifications.send, PASSENGER_PERMS.admin])
  @ApiOperation({ summary: 'Update a notification template (code is immutable)' })
  @ApiBody({ type: UpdateTemplateDto })
  updateTemplate(@Param('id') id: string, @Body() dto: UpdateTemplateDto) {
    return this.service.updateTemplate(id, dto);
  }

  @Get(':passengerId')
  @ApiOperation({ summary: 'Get notifications for passenger' })
  getForPassenger(@Param('passengerId') id: string) {
    return this.service.getForPassenger(id);
  }

  @Patch(':id/read')
  @ApiOperation({ summary: 'Mark notification as read' })
  markRead(@Param('id') id: string) {
    return this.service.markRead(id);
  }

  @Patch(':passengerId/read-all')
  @ApiOperation({ summary: 'Mark all notifications as read' })
  markAllRead(@Param('passengerId') id: string) {
    return this.service.markAllRead(id);
  }

  @Post('send/email')
  @PassengerStaff([PASSENGER_PERMS.notifications.send, PASSENGER_PERMS.admin])
  @ApiOperation({ summary: 'Send a direct email via the email microservice' })
  @ApiBody({ type: SendEmail })
  sendEmail(@Body() dto: SendEmail) {
    return this.emailClient.sendEmail(dto);
  }

  @Post('send/sms')
  @PassengerStaff([PASSENGER_PERMS.notifications.send, PASSENGER_PERMS.admin])
  @ApiOperation({ summary: 'Send a direct SMS via the SMS microservice' })
  @ApiBody({ type: SingleMessageDto })
  sendSms(@Body() dto: SingleMessageDto) {
    return this.smsClient.sendSms(dto);
  }

  @Post('send/sms/bulk')
  @PassengerStaff([PASSENGER_PERMS.notifications.send, PASSENGER_PERMS.admin])
  @ApiOperation({ summary: 'Send bulk SMS messages via the SMS microservice' })
  @ApiBody({ type: BulkMessagesDto })
  sendBulkSms(@Body() dto: BulkMessagesDto) {
    return this.smsClient.sendBulkMessages(dto);
  }

  @Post('test')
  @ApiOperation({ summary: 'Test notification delivery (Admin only)' })
  async testNotification(@Body() dto: TestNotificationDto) {
    return this.service.send(
      dto.templateKey,
      dto.recipient,
      dto.context,
      dto.channels as any,
    );
  }
}
