import { Controller, Get, Post, Patch, Delete, Body, Param, Query, BadRequestException } from '@nestjs/common';
import { ApiTags, ApiOperation, ApiResponse } from '@nestjs/swagger';
import { KnowledgeBaseService } from './knowledge-base.service';
import { QuotaGuardService } from '../membership/quota-guard.service';
import { CurrentUser } from '../../common/decorators/current-user.decorator';
import { PaginationDto } from '../../common/dto/pagination.dto';
import type { UserPayload } from '../../common/types';

@ApiTags('knowledge-base')
@Controller('knowledge-bases')
export class KnowledgeBaseController {
  constructor(
    private readonly service: KnowledgeBaseService,
    private readonly quotaGuard: QuotaGuardService,
  ) {}

  @Post()
  @ApiOperation({ summary: '创建知识库' })
  async create(@CurrentUser() user: UserPayload, @Body() dto: any) {
    const userId = String(user?.id || 'anonymous');
    const opId = `kb_create:${userId}:${Date.now()}`;
    const check = await this.quotaGuard.check(userId, 'knowledge_base_count', opId);
    if (!check.allowed) throw new BadRequestException(this.quotaGuard.buildError(check));
    try {
      const result = await this.service.create(userId, dto);
      this.quotaGuard.confirm(opId).catch(() => {});
      return result;
    } catch { this.quotaGuard.cancel(opId).catch(() => {}); throw new BadRequestException('Knowledge base creation failed'); }
  }

  @Get()
  @ApiOperation({ summary: '获取知识库列表' })
  async findAll(
    @CurrentUser() user: UserPayload,
    @Query() pagination: PaginationDto,
    @Query('visibility') visibility?: string,
    @Query('ownerType') ownerType?: string,
  ) {
    return this.service.findAll(String(user?.id || 'anonymous'), {
      ...pagination,
      visibility,
      ownerType,
    });
  }

  @Get(':id')
  @ApiOperation({ summary: '获取知识库详情' })
  async findOne(@CurrentUser() user: UserPayload, @Param('id') id: string) {
    return this.service.findOne(String(user?.id || 'anonymous'), id);
  }

  @Patch(':id')
  @ApiOperation({ summary: '更新知识库' })
  async update(@CurrentUser() user: UserPayload, @Param('id') id: string, @Body() dto: any) {
    return this.service.update(String(user?.id || 'anonymous'), id, dto);
  }

  @Delete(':id')
  @ApiOperation({ summary: '删除知识库' })
  async remove(@CurrentUser() user: UserPayload, @Param('id') id: string) {
    return this.service.remove(String(user?.id || 'anonymous'), id);
  }

  // ── Folder CRUD ──

  @Get(':id/folders')
  @ApiOperation({ summary: '获取知识库文件夹列表' })
  async folders(@Param('id') id: string) {
    return this.service.getFolders(id);
  }

  @Post(':id/folders')
  @ApiOperation({ summary: '创建文件夹' })
  async createFolder(
    @CurrentUser() user: UserPayload,
    @Param('id') id: string,
    @Body() dto: { name: string; parentId?: string },
  ) {
    return this.service.createFolder(String(user?.id || 'anonymous'), id, dto);
  }

  @Patch(':id/folders/:folderId')
  @ApiOperation({ summary: '更新文件夹' })
  async updateFolder(@Param('folderId') folderId: string, @Body() dto: { name?: string; parentId?: string }) {
    return this.service.updateFolder(folderId, dto);
  }

  @Delete(':id/folders/:folderId')
  @ApiOperation({ summary: '删除文件夹（含子文件夹）' })
  async deleteFolder(@Param('folderId') folderId: string) {
    return this.service.deleteFolder(folderId);
  }

  // ── Pin ──

  @Post(':id/pin')
  @ApiOperation({ summary: '切换置顶状态' })
  async togglePin(@CurrentUser() user: UserPayload, @Param('id') id: string) {
    return this.service.togglePin(String(user?.id || 'anonymous'), id);
  }

  // ── Visibility ──

  @Patch(':id/visibility')
  @ApiOperation({ summary: '切换公开/私有' })
  async setVisibility(
    @CurrentUser() user: UserPayload,
    @Param('id') id: string,
    @Body() dto: { visibility: string },
  ) {
    return this.service.setVisibility(String(user?.id || 'anonymous'), id, dto.visibility);
  }

  // ── Subscribe ──

  @Post(':id/subscribe')
  @ApiOperation({ summary: '订阅知识库' })
  async subscribe(@CurrentUser() user: UserPayload, @Param('id') id: string) {
    return this.service.subscribe(String(user?.id || 'anonymous'), id);
  }

  @Delete(':id/subscribe')
  @ApiOperation({ summary: '取消订阅' })
  async unsubscribe(@CurrentUser() user: UserPayload, @Param('id') id: string) {
    return this.service.unsubscribe(String(user?.id || 'anonymous'), id);
  }

  @Get('subscribed')
  @ApiOperation({ summary: '已订阅知识库列表' })
  async listSubscribed(@CurrentUser() user: UserPayload, @Query() pagination: PaginationDto) {
    return this.service.listSubscribed(String(user?.id || 'anonymous'), pagination);
  }

  // ── Discover ──

  @Get('discover')
  @ApiOperation({ summary: '发现公开知识库' })
  async discover(@Query('search') search?: string, @Query('page') page?: string, @Query('limit') limit?: string) {
    return this.service.discoverPublic({
      page: Number(page) || 1,
      limit: Math.min(Number(limit) || 20, 100),
      search,
    });
  }
}
