import mongoose from 'mongoose';
import { Ticket } from '../models/Ticket';
import { KPI } from '../models/KPI';
import { WorkOrder } from '../models/WorkOrder';
import { FinancialData } from '../models/Financial';
import { Asset } from '../models/Asset';
import { AuditLog } from '../models/AuditLog';
import { Project } from '../models/Project';
import { User } from '../models/User';
import { PMSchedule } from '../models/PMSchedule';

export interface DailyReportData {
  date: Date;
  project: {
    name: string;
    code: string;
  };
  tickets: {
    total: number;
    byStatus: Record<string, number>;
    byPriority: Record<string, number>;
    byCategory: Record<string, number>;
    list: Array<{
      ticketCode: string;
      title: string;
      status: string;
      priority: string;
      category: string;
      createdAt: Date;
    }>;
  };
  workOrders: {
    total: number;
    completed: number;
    inProgress: number;
    totalCost: number;
  };
  summary: {
    openTickets: number;
    resolvedTickets: number;
    completedWorkOrders: number;
  };
}

export interface MonthlyReportData {
  month: string; // YYYY-MM
  project: {
    name: string;
    code: string;
    capacityMWp: number;
  };
  kpi: {
    avgPR: number;
    avgAvailability: number;
    totalProduction: number; // kWh
    avgSpecificYield: number;
    avgIrradiation: number;
  };
  tickets: {
    total: number;
    resolved: number;
    avgResolutionTime: number; // hours
    byCategory: Record<string, number>;
  };
  workOrders: {
    total: number;
    completed: number;
    totalCost: number;
    costBreakdown: {
      labor: number;
      material: number;
      external: number;
    };
    list?: Array<{
      woCode: string;
      title: string;
      workOrderType: string;
      status: string;
      priority: string;
      scheduledStart?: Date | string;
      scheduledEnd?: Date | string;
      actualStart?: Date | string;
      actualEnd?: Date | string;
      costLabor: number;
      costMaterial: number;
      costExternal: number;
      totalCost: number;
      pmSchedule?: {
        frequency: string;
        lastPerformed?: Date;
        nextDue?: Date;
        description?: string;
        title?: string;
      } | null;
      createdAt?: Date | string;
    }>;
  };
  financial: {
    revenue: number;
    opex: number;
    netProfit: number;
  };
}

export interface FinancialReportData {
  period: string;
  project: {
    name: string;
    code: string;
  };
  financials: Array<{
    month: string;
    revenue: number;
    opex: number;
    netProfit: number;
    cumulativeROI: number;
  }>;
  summary: {
    totalRevenue: number;
    totalOpex: number;
    totalNetProfit: number;
    avgROI: number;
    profitMargin: number; // Profit margin percentage
    currentROI: number; // Current cumulative ROI
  };
  costBreakdown: Array<{
    name: string;
    value: number;
  }>;
  screenshot?: string; // Deprecated - will be removed, using direct rendering instead
}

export interface AuditReportData {
  period: {
    start: Date;
    end: Date;
  };
  project?: {
    name: string;
    code: string;
  };
  logs: Array<{
    timestamp: Date;
    user: string;
    action: string;
    targetCollection: string;
    details: string;
  }>;
  summary: {
    totalActions: number;
    byAction: Record<string, number>;
    byCollection: Record<string, number>;
  };
}

export class ReportDataService {
  /**
   * Get data for Daily Report
   */
  static async getDailyReportData(projectId: any, date: Date): Promise<DailyReportData> {
    const startOfDay = new Date(date);
    startOfDay.setHours(0, 0, 0, 0);
    const endOfDay = new Date(date);
    endOfDay.setHours(23, 59, 59, 999);

    // Get project info
    const project = await Project.findById(projectId).lean();
    if (!project) {
      throw new Error('Project not found');
    }

    // Get tickets for the day
    const tickets = await Ticket.find({
      projectId: projectId,
      createdAt: { $gte: startOfDay, $lte: endOfDay }
    }).lean();

    // Get work orders for the day
    // Include work orders that were created, scheduled, or started on this day
    const workOrders = await WorkOrder.find({
      projectId: projectId,
      $or: [
        { createdAt: { $gte: startOfDay, $lte: endOfDay } },
        { scheduledStart: { $gte: startOfDay, $lte: endOfDay } },
        { actualStart: { $gte: startOfDay, $lte: endOfDay } },
        { actualEnd: { $gte: startOfDay, $lte: endOfDay } }
      ]
    }).lean();

    // Process tickets data
    const ticketsByStatus: Record<string, number> = {};
    const ticketsByPriority: Record<string, number> = {};
    const ticketsByCategory: Record<string, number> = {};

    tickets.forEach(ticket => {
      ticketsByStatus[ticket.status] = (ticketsByStatus[ticket.status] || 0) + 1;
      ticketsByPriority[ticket.priority] = (ticketsByPriority[ticket.priority] || 0) + 1;
      ticketsByCategory[ticket.category] = (ticketsByCategory[ticket.category] || 0) + 1;
    });

    const resolvedTickets = tickets.filter(t => t.status === 'Resolved' || t.status === 'Closed').length;

    // Process work orders data
    const completedWorkOrders = workOrders.filter(wo => wo.status === 'Completed' || wo.status === 'Verified').length;
    const totalCost = workOrders.reduce((sum, wo) => sum + (wo.totalCost || 0), 0);

    return {
      date,
      project: {
        name: project.name,
        code: project.code
      },
      tickets: {
        total: tickets.length,
        byStatus: ticketsByStatus,
        byPriority: ticketsByPriority,
        byCategory: ticketsByCategory,
        list: tickets.map(t => ({
          ticketCode: t.ticketCode,
          title: t.title,
          status: t.status,
          priority: t.priority,
          category: t.category,
          createdAt: t.createdAt
        }))
      },
      workOrders: {
        total: workOrders.length,
        completed: completedWorkOrders,
        inProgress: workOrders.filter(wo => wo.status === 'InProgress').length,
        totalCost
      },
      summary: {
        openTickets: tickets.filter(t => t.status === 'Open' || t.status === 'InProgress').length,
        resolvedTickets,
        completedWorkOrders
      }
    };
  }

  /**
   * Get data for Monthly Report
   */
  static async getMonthlyReportData(projectId: any, month: string): Promise<MonthlyReportData> {
    const [year, monthNum] = month.split('-').map(Number);
    const startOfMonth = new Date(year, monthNum - 1, 1);
    const endOfMonth = new Date(year, monthNum, 0, 23, 59, 59, 999);

    // Get project info - handle both ObjectId and string ID
    let project: any;
    if (mongoose.Types.ObjectId.isValid(projectId)) {
      project = await Project.findById(projectId).lean();
    } else {
      // Use native query for string IDs
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const projectsCollection = mongoose.connection.db.collection('projects');
      project = await projectsCollection.findOne({ _id: projectId });
    }
    
    if (!project) {
      throw new Error('Project not found');
    }

    // Get KPI data for the month - handle both ObjectId and string ID
    let kpis: any[];
    if (mongoose.Types.ObjectId.isValid(projectId)) {
      kpis = await KPI.find({
        siteId: new mongoose.Types.ObjectId(projectId),
        date: { $gte: startOfMonth, $lte: endOfMonth }
      }).lean();
    } else {
      // Use native query for string IDs (demo data)
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const kpisCollection = mongoose.connection.db.collection('kpis');
      kpis = await kpisCollection.find({
        siteId: projectId, // Use string directly for demo data
        date: { $gte: startOfMonth, $lte: endOfMonth }
      }).toArray();
    }

    // Calculate KPI averages
    const avgPR = kpis.length > 0 
      ? kpis.reduce((sum, k) => sum + (k.pr || 0), 0) / kpis.length 
      : 0;
    const avgAvailability = kpis.length > 0
      ? kpis.reduce((sum, k) => sum + (k.availability || 0), 0) / kpis.length
      : 0;
    const totalProduction = kpis.reduce((sum, k) => sum + (k.production || 0), 0);
    const avgSpecificYield = kpis.length > 0
      ? kpis.reduce((sum, k) => sum + (k.specificYield || 0), 0) / kpis.length
      : 0;
    const avgIrradiation = kpis.length > 0
      ? kpis.reduce((sum, k) => sum + (k.irradiation || 0), 0) / kpis.length
      : 0;

    // Get tickets for the month - handle both ObjectId and string ID
    let tickets: any[];
    if (mongoose.Types.ObjectId.isValid(projectId)) {
      tickets = await Ticket.find({
        projectId: new mongoose.Types.ObjectId(projectId),
        createdAt: { $gte: startOfMonth, $lte: endOfMonth }
      }).lean();
    } else {
      // Use native query for string IDs
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const ticketsCollection = mongoose.connection.db.collection('tickets');
      tickets = await ticketsCollection.find({
        projectId: projectId,
        createdAt: { $gte: startOfMonth, $lte: endOfMonth }
      }).toArray();
    }

    const resolvedTickets = tickets.filter(t => t.status === 'Resolved' || t.status === 'Closed');
    const ticketsByCategory: Record<string, number> = {};
    tickets.forEach(t => {
      ticketsByCategory[t.category] = (ticketsByCategory[t.category] || 0) + 1;
    });

    // Calculate average resolution time (simplified - using createdAt and updatedAt)
    let avgResolutionTime = 0;
    if (resolvedTickets.length > 0) {
      const totalHours = resolvedTickets.reduce((sum, t) => {
        const created = new Date(t.createdAt).getTime();
        const updated = new Date(t.updatedAt).getTime();
        return sum + (updated - created) / (1000 * 60 * 60); // Convert to hours
      }, 0);
      avgResolutionTime = totalHours / resolvedTickets.length;
    }

    // Get work orders for the month - handle both ObjectId and string ID
    // Strategy: Get all work orders for the project, then filter by any date field in the month
    let allWorkOrders: any[];
    
    if (mongoose.Types.ObjectId.isValid(projectId)) {
      // Try both ObjectId and string format for projectId
      allWorkOrders = await WorkOrder.find({
        $or: [
          { projectId: new mongoose.Types.ObjectId(projectId) },
          { projectId: projectId.toString() }
        ]
      }).lean();
    } else {
      // Use native query for string IDs
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const workOrdersCollection = mongoose.connection.db.collection('workOrders');
      
      // Try both string and ObjectId format
      const objectIdProjectId = mongoose.Types.ObjectId.isValid(projectId) 
        ? new mongoose.Types.ObjectId(projectId) 
        : null;
      
      const query: any = {
        $or: [
          { projectId: projectId }
        ]
      };
      
      if (objectIdProjectId) {
        query.$or.push({ projectId: objectIdProjectId });
      }
      
      allWorkOrders = await workOrdersCollection.find(query).toArray();
    }
    
    // Filter work orders that have any date field within the month
    const workOrders = allWorkOrders.filter(wo => {
      // Check createdAt
      if (wo.createdAt) {
        const woDate = new Date(wo.createdAt);
        if (woDate >= startOfMonth && woDate <= endOfMonth) return true;
      }
      
      // Check scheduledStart
      if (wo.scheduledStart) {
        const woDate = new Date(wo.scheduledStart);
        if (woDate >= startOfMonth && woDate <= endOfMonth) return true;
      }
      
      // Check actualStart
      if (wo.actualStart) {
        const woDate = new Date(wo.actualStart);
        if (woDate >= startOfMonth && woDate <= endOfMonth) return true;
      }
      
      // Check actualEnd
      if (wo.actualEnd) {
        const woDate = new Date(wo.actualEnd);
        if (woDate >= startOfMonth && woDate <= endOfMonth) return true;
      }
      
      return false;
    });

    // Get PM schedules to enrich work orders with frequency and timing info
    let pmSchedules: any[] = [];
    try {
      if (mongoose.Types.ObjectId.isValid(projectId)) {
        pmSchedules = await PMSchedule.find({
          projectId: new mongoose.Types.ObjectId(projectId),
          status: 'Active'
        }).lean();
      } else {
        if (mongoose.connection.db) {
          const pmSchedulesCollection = mongoose.connection.db.collection('pmschedules');
          pmSchedules = await pmSchedulesCollection.find({
            projectId: projectId,
            status: 'Active'
          }).toArray();
        }
      }
    } catch (pmError) {
      console.warn('Error fetching PM schedules for report:', pmError);
    }

    // Enrich work orders with PM schedule info
    const enrichedWorkOrders = workOrders.map(wo => {
      let pmScheduleInfo = null;
      
      // Find related PM schedule for PM work orders
      if (wo.workOrderType === 'PM' && wo.contractId) {
        const matchingSchedule = pmSchedules.find(s => {
          // Match by contractId and title
          if (s.contractId?.toString() === wo.contractId?.toString()) {
            // Check if work order title contains schedule title
            if (wo.title?.includes(s.title)) {
              return true;
            }
            // Check if work order title starts with "Bảo trì định kỳ:"
            if (wo.title?.startsWith('Bảo trì định kỳ:')) {
              const scheduleTitle = wo.title.replace('Bảo trì định kỳ:', '').trim();
              if (scheduleTitle === s.title) {
                return true;
              }
            }
          }
          return false;
        });
        
        if (matchingSchedule) {
          pmScheduleInfo = {
            frequency: matchingSchedule.frequency,
            lastPerformed: matchingSchedule.lastPerformed,
            nextDue: matchingSchedule.nextDue,
            description: matchingSchedule.description,
            title: matchingSchedule.title
          };
        }
      }
      
      return {
        ...wo,
        pmSchedule: pmScheduleInfo
      };
    });

    const completedWorkOrders = enrichedWorkOrders.filter(wo => wo.status === 'Completed' || wo.status === 'Verified');
    const totalCost = enrichedWorkOrders.reduce((sum, wo) => sum + (wo.totalCost || 0), 0);
    const costBreakdown = {
      labor: enrichedWorkOrders.reduce((sum, wo) => sum + (wo.costLabor || 0), 0),
      material: enrichedWorkOrders.reduce((sum, wo) => sum + (wo.costMaterial || 0), 0),
      external: enrichedWorkOrders.reduce((sum, wo) => sum + (wo.costExternal || 0), 0)
    };

    // Get financial data for the month - handle both ObjectId and string ID
    let financial: any;
    if (mongoose.Types.ObjectId.isValid(projectId)) {
      financial = await FinancialData.findOne({
        projectId: new mongoose.Types.ObjectId(projectId),
        month: month
      }).lean();
    } else {
      // Use native query for string IDs
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const financialsCollection = mongoose.connection.db.collection('financials');
      financial = await financialsCollection.findOne({
        projectId: projectId,
        month: month
      });
    }

    return {
      month,
      project: {
        name: project.name,
        code: project.code,
        capacityMWp: project.capacityMWp || 0
      },
      kpi: {
        avgPR: Math.round(avgPR * 100) / 100,
        avgAvailability: Math.round(avgAvailability * 100) / 100,
        totalProduction: Math.round(totalProduction),
        avgSpecificYield: Math.round(avgSpecificYield * 100) / 100,
        avgIrradiation: Math.round(avgIrradiation * 100) / 100
      },
      tickets: {
        total: tickets.length,
        resolved: resolvedTickets.length,
        avgResolutionTime: Math.round(avgResolutionTime * 100) / 100,
        byCategory: ticketsByCategory
      },
      workOrders: {
        total: enrichedWorkOrders.length,
        completed: completedWorkOrders.length,
        totalCost,
        costBreakdown,
        list: enrichedWorkOrders.map(wo => ({
          woCode: wo.woCode,
          title: wo.title,
          workOrderType: wo.workOrderType || wo.type,
          status: wo.status,
          priority: wo.priority,
          scheduledStart: wo.scheduledStart || wo.scheduledDate,
          scheduledEnd: wo.scheduledEnd,
          actualStart: wo.actualStart,
          actualEnd: wo.actualEnd,
          costLabor: wo.costLabor || 0,
          costMaterial: wo.costMaterial || 0,
          costExternal: wo.costExternal || 0,
          totalCost: wo.totalCost || 0,
          pmSchedule: wo.pmSchedule,
          createdAt: wo.createdAt
        }))
      },
      financial: {
        revenue: financial?.revenue || 0,
        opex: financial?.opex || 0,
        netProfit: financial?.netProfit || 0
      }
    };
  }

  /**
   * Get data for Financial Report
   */
  static async getFinancialReportData(projectId: any, startMonth: string, endMonth: string): Promise<FinancialReportData> {
    // Get project info - handle both ObjectId and string ID
    let project: any;
    if (mongoose.Types.ObjectId.isValid(projectId)) {
      project = await Project.findById(projectId).lean();
    } else {
      // Use native query for string IDs
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const projectsCollection = mongoose.connection.db.collection('projects');
      project = await projectsCollection.findOne({ _id: projectId });
    }
    
    if (!project) {
      throw new Error('Project not found');
    }

    // Get financial data for the period - handle both ObjectId and string ID
    let financials: any[];
    if (mongoose.Types.ObjectId.isValid(projectId)) {
      financials = await FinancialData.find({
        projectId: new mongoose.Types.ObjectId(projectId),
        month: { $gte: startMonth, $lte: endMonth }
      }).sort({ month: 1 }).lean();
    } else {
      // Use native query for string IDs
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const financialsCollection = mongoose.connection.db.collection('financials');
      financials = await financialsCollection.find({
        projectId: projectId,
        month: { $gte: startMonth, $lte: endMonth }
      }).sort({ month: 1 }).toArray();
    }

    const totalRevenue = financials.reduce((sum, f) => sum + (f.revenue || 0), 0);
    const totalOpex = financials.reduce((sum, f) => sum + (f.opex || 0), 0);
    const totalNetProfit = financials.reduce((sum, f) => sum + (f.netProfit || 0), 0);
    const avgROI = financials.length > 0
      ? financials.reduce((sum, f) => sum + (f.cumulativeROI || 0), 0) / financials.length
      : 0;
    const currentROI = financials.length > 0 ? financials[financials.length - 1].cumulativeROI || 0 : 0;
    const profitMargin = totalRevenue > 0 ? (totalNetProfit / totalRevenue) * 100 : 0;

    // Cost breakdown data (mock data structure - can be enhanced with actual breakdown)
    const costBreakdown = [
      { name: 'Nhân sự O&M', value: totalOpex * 0.35 },
      { name: 'Vật tư thay thế', value: totalOpex * 0.20 },
      { name: 'Vệ sinh tấm pin', value: totalOpex * 0.15 },
      { name: 'Bảo hiểm', value: totalOpex * 0.10 },
      { name: 'Thuê đất', value: totalOpex * 0.10 },
      { name: 'Khác', value: totalOpex * 0.10 }
    ].filter(item => item.value > 0); // Only include non-zero items

    return {
      period: `${startMonth} to ${endMonth}`,
      project: {
        name: project.name,
        code: project.code
      },
      financials: financials.map(f => ({
        month: f.month,
        revenue: f.revenue || 0,
        opex: f.opex || 0,
        netProfit: f.netProfit || 0,
        cumulativeROI: f.cumulativeROI || 0
      })),
      summary: {
        totalRevenue,
        totalOpex,
        totalNetProfit,
        avgROI: Math.round(avgROI * 100) / 100,
        profitMargin: Math.round(profitMargin * 100) / 100,
        currentROI: Math.round(currentROI * 100) / 100
      },
      costBreakdown
    };
  }

  /**
   * Get data for Audit Report
   */
  static async getAuditReportData(projectId: any | undefined, startDate: Date, endDate: Date): Promise<AuditReportData> {
    const query: any = {
      timestamp: { $gte: startDate, $lte: endDate }
    };

    // If projectId is provided, filter by project-related collections
    if (projectId) {
      // Get project - handle both ObjectId and string ID
      let project: any;
      if (mongoose.Types.ObjectId.isValid(projectId)) {
        project = await Project.findById(projectId).lean();
      } else {
        // Use native query for string IDs
        if (!mongoose.connection.db) {
          throw new Error('Database connection not established');
        }
        const projectsCollection = mongoose.connection.db.collection('projects');
        project = await projectsCollection.findOne({ _id: projectId });
      }
      
      if (project) {
        // Get IDs from related collections - handle both ObjectId and string ID
        let ticketIds: any[];
        let workOrderIds: any[];
        
        if (mongoose.Types.ObjectId.isValid(projectId)) {
          ticketIds = await Ticket.find({ projectId: new mongoose.Types.ObjectId(projectId) }).distinct('_id');
          workOrderIds = await WorkOrder.find({ projectId: new mongoose.Types.ObjectId(projectId) }).distinct('_id');
        } else {
          // Use native query for string IDs
          const db = mongoose.connection.db;
          if (!db) {
            throw new Error('Database connection not established');
          }
          const ticketsCollection = db.collection('tickets');
          const workOrdersCollection = db.collection('workOrders');
          ticketIds = await ticketsCollection.distinct('_id', { projectId });
          workOrderIds = await workOrdersCollection.distinct('_id', { projectId });
        }

        const db = mongoose.connection.db;
        if (!db) throw new Error('Database connection not established');
        const assetsCollection = db.collection('assets');
        const assets = await assetsCollection.find({ projectId }).toArray();
        const assetIds = assets.map((a: any) => a._id);

        // Build OR query
        const orConditions: any[] = [];
        if (ticketIds.length > 0) {
          orConditions.push({ targetCollection: 'tickets', targetId: { $in: ticketIds } });
        }
        if (workOrderIds.length > 0) {
          orConditions.push({ targetCollection: 'workOrders', targetId: { $in: workOrderIds } });
        }
        if (assetIds.length > 0) {
          orConditions.push({ targetCollection: 'assets', targetId: { $in: assetIds } });
        }

        if (orConditions.length > 0) {
          query.$or = orConditions;
        } else {
          // If no related data found, return empty result
          query._id = { $exists: false }; // This will return no results
        }
      }
    }

    const logs = await AuditLog.find(query)
      .sort({ timestamp: -1 })
      .limit(1000)
      .lean();

    // Get user info for logs - handle both ObjectId and string IDs
    const userIds = [...new Set(logs.map(l => l.userId))];
    let users: any[];
    const validObjectIds = userIds.filter(id => mongoose.Types.ObjectId.isValid(id));
    const stringIds = userIds.filter(id => !mongoose.Types.ObjectId.isValid(id));
    
    if (validObjectIds.length > 0 && stringIds.length > 0) {
      // Mixed IDs - query both ways
      const objectIdUsers = await User.find({ _id: { $in: validObjectIds.map(id => new mongoose.Types.ObjectId(id)) } }).lean();
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const usersCollection = mongoose.connection.db.collection('users');
      const stringUsers = await usersCollection.find({ _id: { $in: stringIds } }).toArray();
      users = [...objectIdUsers, ...stringUsers];
    } else if (validObjectIds.length > 0) {
      users = await User.find({ _id: { $in: validObjectIds.map(id => new mongoose.Types.ObjectId(id)) } }).lean();
    } else if (stringIds.length > 0) {
      if (!mongoose.connection.db) {
        throw new Error('Database connection not established');
      }
      const usersCollection = mongoose.connection.db.collection('users');
      users = await usersCollection.find({ _id: { $in: stringIds } }).toArray();
    } else {
      users = [];
    }
    
    const userMap = new Map(users.map((u: any) => [u._id.toString(), u.email || u.name || 'Unknown']));

    const byAction: Record<string, number> = {};
    const byCollection: Record<string, number> = {};

    logs.forEach(log => {
      byAction[log.action] = (byAction[log.action] || 0) + 1;
      byCollection[log.targetCollection] = (byCollection[log.targetCollection] || 0) + 1;
    });

    // Get project - handle both ObjectId and string ID
    let project: any = null;
    if (projectId) {
      if (mongoose.Types.ObjectId.isValid(projectId)) {
        project = await Project.findById(projectId).lean();
      } else {
        // Use native query for string IDs
        if (!mongoose.connection.db) {
          throw new Error('Database connection not established');
        }
        const projectsCollection = mongoose.connection.db.collection('projects');
        project = await projectsCollection.findOne({ _id: projectId });
      }
    }

    return {
      period: {
        start: startDate,
        end: endDate
      },
      project: project ? {
        name: project.name,
        code: project.code
      } : undefined,
      logs: logs.map(log => ({
        timestamp: log.timestamp,
        user: userMap.get(log.userId.toString()) || 'Unknown',
        action: log.action,
        targetCollection: log.targetCollection,
        details: log.details
      })),
      summary: {
        totalActions: logs.length,
        byAction,
        byCollection
      }
    };
  }
}
