/**
 * 管理员操作日志装饰器
 * 
 * 功能描述：
 * - 自动记录管理员的数据库操作
 * - 支持操作前后数据状态记录
 * - 提供灵活的配置选项
 * - 集成错误处理和性能监控
 * 
 * 使用方式：
 * @LogAdminOperation({
 *   operationType: 'CREATE',
 *   targetType: 'users',
 *   description: '创建用户',
 *   isSensitive: true
 * })
 * 
 * 最近修改：
 * - 2026-01-08: 注释规范优化 - 修正@author字段，更新版本号和修改记录 (修改者: moyin)
 * - 2026-01-08: 注释规范优化 - 为接口添加注释，完善文档说明 (修改者: moyin)
 * - 2026-01-08: 功能新增 - 创建管理员操作日志装饰器 (修改者: assistant)
 * 
 * @author moyin
 * @version 1.0.2
 * @since 2026-01-08
 * @lastModified 2026-01-08
 */

import { SetMetadata, createParamDecorator, ExecutionContext } from '@nestjs/common';
import { OPERATION_TYPES } from './admin_constants';

/**
 * 管理员操作日志装饰器配置选项
 * 
 * 功能描述：
 * 定义管理员操作日志装饰器的配置参数
 * 
 * 使用场景：
 * - 配置@LogAdminOperation装饰器的行为
 * - 指定操作类型、目标类型和敏感性等属性
 */
export interface LogAdminOperationOptions {
  operationType: keyof typeof OPERATION_TYPES;
  targetType: string;
  description: string;
  isSensitive?: boolean;
  captureBeforeData?: boolean;
  captureAfterData?: boolean;
  captureRequestParams?: boolean;
}

export const LOG_ADMIN_OPERATION_KEY = 'log_admin_operation';

/**
 * 管理员操作日志装饰器
 * 
 * @param options 日志配置选项
 * @returns 装饰器函数
 */
export const LogAdminOperation = (options: LogAdminOperationOptions) => {
  return SetMetadata(LOG_ADMIN_OPERATION_KEY, options);
};

/**
 * 获取当前管理员信息的参数装饰器
 */
export const CurrentAdmin = createParamDecorator(
  (data: unknown, ctx: ExecutionContext) => {
    const request = ctx.switchToHttp().getRequest();
    return request.user; // 假设JWT认证后用户信息存储在request.user中
  },
);

/**
 * 获取客户端IP地址的参数装饰器
 */
export const ClientIP = createParamDecorator(
  (data: unknown, ctx: ExecutionContext) => {
    const request = ctx.switchToHttp().getRequest();
    return request.ip || 
           request.connection?.remoteAddress || 
           request.socket?.remoteAddress ||
           (request.connection?.socket as any)?.remoteAddress ||
           request.headers['x-forwarded-for']?.split(',')[0] ||
           request.headers['x-real-ip'] ||
           'unknown';
  },
);

/**
 * 获取用户代理的参数装饰器
 */
export const UserAgent = createParamDecorator(
  (data: unknown, ctx: ExecutionContext) => {
    const request = ctx.switchToHttp().getRequest();
    return request.headers['user-agent'] || 'unknown';
  },
);