import { Body, Controller, Delete, Get, Headers, Param, Patch, Post, Query } from '@nestjs/common';
import { JwtService } from '@nestjs/jwt';
import { ApiBearerAuth, ApiOperation, ApiTags } from '@nestjs/swagger';
import { firstValueFrom } from 'rxjs';
import { map } from 'rxjs/operators';
import { CoreGrpcService } from '../core-grpc.service';
import { getAuthorizedUserId } from '../document-access';
import { MarkNotificationReadDto } from '../dto/notifications.dto';

@ApiTags('Уведомления')
@ApiBearerAuth()
@Controller('notifications')
export class NotificationsController {
  constructor(
    private readonly core: CoreGrpcService,
    private readonly jwt: JwtService
  ) {}

  @Get()
  @ApiOperation({ summary: 'Список уведомлений' })
  async list(
    @Headers('authorization') authorization: string | undefined,
    @Query('limit') limit?: string,
    @Query('unreadOnly') unreadOnly?: string
  ) {
    const userId = await getAuthorizedUserId(this.jwt, this.core, authorization);
    return firstValueFrom(
      this.core.notifications.ListNotifications({
        userId,
        limit: limit ? Number(limit) : 30,
        unreadOnly: unreadOnly === 'true'
      }).pipe(
        map((response) => {
          const payload = response as { notifications?: unknown[] };
          return { notifications: payload.notifications ?? [] };
        })
      )
    );
  }

  @Get('unread-count')
  @ApiOperation({ summary: 'Количество непрочитанных уведомлений' })
  async unreadCount(@Headers('authorization') authorization: string | undefined) {
    const userId = await getAuthorizedUserId(this.jwt, this.core, authorization);
    return firstValueFrom(this.core.notifications.GetUnreadCount({ userId }));
  }

  @Patch(':notificationId/read')
  @ApiOperation({ summary: 'Удалить просмотренное уведомление' })
  async markRead(
    @Headers('authorization') authorization: string | undefined,
    @Param('notificationId') notificationId: string,
    @Body() _dto: MarkNotificationReadDto
  ) {
    const userId = await getAuthorizedUserId(this.jwt, this.core, authorization);
    return firstValueFrom(this.core.notifications.DeleteNotification({ userId, notificationId }));
  }

  @Delete(':notificationId')
  @ApiOperation({ summary: 'Удалить уведомление' })
  async deleteNotification(
    @Headers('authorization') authorization: string | undefined,
    @Param('notificationId') notificationId: string
  ) {
    const userId = await getAuthorizedUserId(this.jwt, this.core, authorization);
    return firstValueFrom(this.core.notifications.DeleteNotification({ userId, notificationId }));
  }

  @Post('read-all')
  @ApiOperation({ summary: 'Удалить все уведомления' })
  async markAllRead(@Headers('authorization') authorization: string | undefined) {
    const userId = await getAuthorizedUserId(this.jwt, this.core, authorization);
    return firstValueFrom(this.core.notifications.DeleteAllNotifications({ userId }));
  }

  @Delete()
  @ApiOperation({ summary: 'Удалить все уведомления' })
  async deleteAll(@Headers('authorization') authorization: string | undefined) {
    const userId = await getAuthorizedUserId(this.jwt, this.core, authorization);
    return firstValueFrom(this.core.notifications.DeleteAllNotifications({ userId }));
  }
}
