import {
  WebSocketGateway,
  WebSocketServer,
  SubscribeMessage,
  MessageBody,
  ConnectedSocket,
  OnGatewayConnection,
  OnGatewayDisconnect,
} from '@nestjs/websockets';
import { Server, Socket } from 'socket.io';
import { Logger, UseGuards } from '@nestjs/common';
import { ConfigService } from '@nestjs/config';
import { MarketService } from './market.service';
import { WsJwtGuard } from './guards/ws-jwt.guard';

interface SubscribeMessageData {
  symbols: string[];
  channels: ('tick' | 'kline' | 'depth')[];
}

@WebSocketGateway({
  namespace: 'market',
  cors: {
    origin: '*',
  },
})
export class MarketGateway implements OnGatewayConnection, OnGatewayDisconnect {
  @WebSocketServer()
  server: Server;

  private readonly logger = new Logger(MarketGateway.name);
  private clientSubscriptions: Map<string, Set<string>> = new Map(); // clientId -> symbols

  constructor(
    private readonly configService: ConfigService,
    private readonly marketService: MarketService,
  ) {}

  handleConnection(client: Socket) {
    this.logger.log(`客户端连接: ${client.id}`);
    this.clientSubscriptions.set(client.id, new Set());
  }

  handleDisconnect(client: Socket) {
    this.logger.log(`客户端断开: ${client.id}`);
    this.clientSubscriptions.delete(client.id);
  }

  @SubscribeMessage('subscribe')
  async handleSubscribe(
    @MessageBody() data: SubscribeMessageData,
    @ConnectedSocket() client: Socket,
  ) {
    const { symbols, channels } = data;
    const subscriptions = this.clientSubscriptions.get(client.id) || new Set();

    symbols.forEach((symbol) => {
      subscriptions.add(symbol);
      
      // 加入品种房间
      client.join(`symbol:${symbol}`);
      
      // 根据频道加入对应房间
      channels.forEach((channel) => {
        client.join(`${channel}:${symbol}`);
      });
    });

    this.clientSubscriptions.set(client.id, subscriptions);

    // 发送当前数据
    const ticks = await this.marketService.getBatchTicks(symbols);
    
    client.emit('subscribed', {
      symbols,
      channels,
      initialData: ticks,
    });

    this.logger.log(`客户端 ${client.id} 订阅: ${symbols.join(', ')}`);
  }

  @SubscribeMessage('unsubscribe')
  handleUnsubscribe(
    @MessageBody() data: { symbols: string[] },
    @ConnectedSocket() client: Socket,
  ) {
    const { symbols } = data;
    const subscriptions = this.clientSubscriptions.get(client.id) || new Set();

    symbols.forEach((symbol) => {
      subscriptions.delete(symbol);
      client.leave(`symbol:${symbol}`);
      client.leave(`tick:${symbol}`);
      client.leave(`kline:${symbol}`);
      client.leave(`depth:${symbol}`);
    });

    this.clientSubscriptions.set(client.id, subscriptions);
    client.emit('unsubscribed', { symbols });
  }

  // 广播Tick数据
  broadcastTick(symbol: string, data: any) {
    this.server.to(`tick:${symbol}`).emit('tick', {
      symbol,
      data,
      timestamp: Date.now(),
    });
  }

  // 广播K线数据
  broadcastKline(symbol: string, period: string, data: any) {
    this.server.to(`kline:${symbol}`).emit('kline', {
      symbol,
      period,
      data,
      timestamp: Date.now(),
    });
  }

  // 广播市场概览
  broadcastMarketOverview(data: any) {
    this.server.emit('market:overview', {
      data,
      timestamp: Date.now(),
    });
  }

  // 获取在线客户端数量
  getConnectedClientsCount(): number {
    return this.clientSubscriptions.size;
  }
}
