import {
  Body,
  Controller,
  Delete,
  Get,
  Param,
  Patch,
  Post,
  Query,
  UseGuards,
} from '@nestjs/common';
import { ApiBearerAuth, ApiTags } from '@nestjs/swagger';
import { TripStatus } from '../common/constants/enums';
import { CurrentUser } from '../common/decorators/current-user.decorator';
import type { JwtUserPayload } from '../auth/jwt.types';
import { TripsService } from './trips.service';
import {
  UpdateTripDto,
  UpdateTripStatusDto,
} from './dto/trip.dto';
import { normalizeCreateTripInput } from './trip-api.mapper';

@ApiTags('trips')
@ApiBearerAuth('access-token')
@Controller('trips')
export class TripsController {
  constructor(private readonly trips: TripsService) {}

  @Post()
  create(
    @CurrentUser() actor: JwtUserPayload,
    @Body() body: Record<string, unknown>,
  ) {
    return this.trips.create(actor, normalizeCreateTripInput(body));
  }

  @Get()
  list(
    @CurrentUser() actor: JwtUserPayload,
    @Query('userId') userId?: string,
    @Query('status') status?: TripStatus,
    @Query('from') from?: string,
    @Query('to') to?: string,
    @Query('cursor') cursor?: string,
    @Query('limit') limit?: string,
  ) {
    return this.trips.list(actor, {
      userId,
      status,
      from,
      to,
      cursor,
      limit: limit ? Number(limit) : undefined,
    });
  }

  @Get(':tripId')
  getOne(
    @Param('tripId') tripId: string,
    @CurrentUser() actor: JwtUserPayload,
  ) {
    return this.trips.getOne(tripId, actor);
  }

  @Patch(':tripId')
  update(
    @Param('tripId') tripId: string,
    @CurrentUser() actor: JwtUserPayload,
    @Body() dto: UpdateTripDto,
  ) {
    return this.trips.update(tripId, actor, dto);
  }

  @Delete(':tripId')
  remove(
    @Param('tripId') tripId: string,
    @CurrentUser() actor: JwtUserPayload,
  ) {
    return this.trips.remove(tripId, actor);
  }

  @Post(':tripId/status')
  updateStatus(
    @Param('tripId') tripId: string,
    @CurrentUser() actor: JwtUserPayload,
    @Body() dto: UpdateTripStatusDto,
  ) {
    return this.trips.updateStatus(tripId, dto.status, actor);
  }
}
