import { Injectable, Logger } from '@nestjs/common';
import { PrismaService } from '@core/database/prisma/prisma.service';

export interface RecentlyVisitedItem {
  id: string;
  type: 'document' | 'article';
  title: string;
  webUrl?: string;
  lastViewedAt: Date;
  editedAt?: Date;
  docType?: string;
}

export interface ActivityItem {
  id: string;
  type: 'comment' | 'mention' | 'like';
  actorId: string;
  actorName: string;
  targetType: 'document' | 'article';
  targetId: string;
  targetTitle: string;
  content?: string;
  createdAt: Date;
  isRead?: boolean;
}

export interface AnalyticsData {
  createdArticles: {
    draft: number;
    published: number;
  };
  views: number;
  reads: number;
  likes: number;
  dislikes: number;
}

@Injectable()
export class ActivityService {
  private readonly logger = new Logger(ActivityService.name);

  constructor(private readonly prisma: PrismaService) {}

  /**
   * 获取用户最近访问的文档
   */
  async getRecentlyVisited(userId: string, limit: number = 6): Promise<RecentlyVisitedItem[]> {
    const views = await this.prisma.documentView.findMany({
      where: { userId },
      orderBy: { viewedAt: 'desc' },
      take: limit * 2, // 取多一些用于去重
      include: {
        spDocument: {
          select: {
            id: true,
            title: true,
            webUrl: true,
            docType: true,
            spModifiedAt: true,
          },
        },
        article: {
          select: {
            id: true,
            title: true,
            updatedAt: true,
          },
        },
      },
    });

    // 去重并映射
    const seen = new Set<string>();
    const items: RecentlyVisitedItem[] = [];

    for (const view of views) {
      if (items.length >= limit) break;

      if (view.spDocument && !seen.has(view.spDocument.id)) {
        seen.add(view.spDocument.id);
        items.push({
          id: view.spDocument.id,
          type: 'document',
          title: view.spDocument.title,
          webUrl: view.spDocument.webUrl,
          lastViewedAt: view.viewedAt,
          editedAt: view.spDocument.spModifiedAt ?? undefined,
          docType: view.spDocument.docType,
        });
      } else if (view.article && !seen.has(view.article.id)) {
        seen.add(view.article.id);
        items.push({
          id: view.article.id,
          type: 'article',
          title: view.article.title,
          lastViewedAt: view.viewedAt,
          editedAt: view.article.updatedAt,
          docType: 'ARTICLE',
        });
      }
    }

    return items;
  }

  /**
   * 记录文档浏览
   */
  async recordView(
    userId: string,
    targetType: 'document' | 'article',
    targetId: string,
  ): Promise<void> {
    const today = new Date();
    today.setHours(0, 0, 0, 0);

    const data = {
      userId,
      viewedAt: new Date(),
      viewDate: today,
      ...(targetType === 'document'
        ? { spDocumentId: targetId }
        : { articleId: targetId }),
    };

    // Upsert：如果今天已访问过，更新时间；否则创建新记录
    await this.prisma.documentView.upsert({
      where:
        targetType === 'document'
          ? { spDocumentId_userId_viewDate: { spDocumentId: targetId, userId, viewDate: today } }
          : { articleId_userId_viewDate: { articleId: targetId, userId, viewDate: today } },
      update: { viewedAt: new Date() },
      create: data,
    });
  }

  /**
   * 获取活动动态
   */
  async getActivityFeed(
    userId: string,
    options: {
      filter?: 'all' | 'mentions' | 'comments';
      limit?: number;
    } = {},
  ): Promise<ActivityItem[]> {
    const { filter = 'all', limit = 20 } = options;

    const items: ActivityItem[] = [];

    // 获取 @提及
    if (filter === 'all' || filter === 'mentions') {
      const mentions = await this.prisma.userMention.findMany({
        where: { mentionedUserId: userId },
        orderBy: { createdAt: 'desc' },
        take: limit,
        include: {
          comment: {
            include: {
              user: { select: { id: true, displayName: true } },
              spDocument: { select: { id: true, title: true } },
              article: { select: { id: true, title: true } },
            },
          },
        },
      });

      for (const mention of mentions) {
        const target = mention.comment.spDocument || mention.comment.article;
        if (!target) continue;

        items.push({
          id: mention.id,
          type: 'mention',
          actorId: mention.comment.user.id,
          actorName: mention.comment.user.displayName ?? 'Unknown',
          targetType: mention.comment.spDocument ? 'document' : 'article',
          targetId: target.id,
          targetTitle: target.title,
          content: mention.comment.content.substring(0, 200),
          createdAt: mention.createdAt,
          isRead: !!mention.readAt,
        });
      }
    }

    // 获取评论（用户文档上的评论）
    if (filter === 'all' || filter === 'comments') {
      // 获取用户创建的文章上的评论
      const myArticleIds = await this.prisma.knowledgeArticle.findMany({
        where: { createdById: userId },
        select: { id: true },
      });

      if (myArticleIds.length > 0) {
        const comments = await this.prisma.documentComment.findMany({
          where: {
            articleId: { in: myArticleIds.map((a) => a.id) },
            userId: { not: userId }, // 排除自己的评论
            deletedAt: null,
          },
          orderBy: { createdAt: 'desc' },
          take: limit,
          include: {
            user: { select: { id: true, displayName: true } },
            article: { select: { id: true, title: true } },
          },
        });

        for (const comment of comments) {
          if (!comment.article) continue;

          items.push({
            id: comment.id,
            type: 'comment',
            actorId: comment.user.id,
            actorName: comment.user.displayName ?? 'Unknown',
            targetType: 'article',
            targetId: comment.article.id,
            targetTitle: comment.article.title,
            content: comment.content.substring(0, 200),
            createdAt: comment.createdAt,
          });
        }
      }
    }

    // 按时间排序
    items.sort((a, b) => b.createdAt.getTime() - a.createdAt.getTime());

    return items.slice(0, limit);
  }

  /**
   * 标记提及为已读
   */
  async markMentionAsRead(mentionId: string, userId: string): Promise<void> {
    await this.prisma.userMention.updateMany({
      where: {
        id: mentionId,
        mentionedUserId: userId,
      },
      data: { readAt: new Date() },
    });
  }

  /**
   * 获取用户 Analytics 数据
   */
  async getUserAnalytics(userId: string): Promise<AnalyticsData> {
    const [articleStats, viewCount, likeStats] = await Promise.all([
      // 文章统计
      this.prisma.knowledgeArticle.groupBy({
        by: ['status'],
        where: { createdById: userId, deletedAt: null },
        _count: true,
      }),
      // 浏览量（用户文章的总浏览量）
      this.prisma.documentView.count({
        where: {
          article: { createdById: userId },
        },
      }),
      // 点赞统计
      this.prisma.documentLike.groupBy({
        by: ['type'],
        where: {
          article: { createdById: userId },
        },
        _count: true,
      }),
    ]);

    const createdArticles = { draft: 0, published: 0 };
    for (const stat of articleStats) {
      if (stat.status === 'DRAFT') {
        createdArticles.draft = stat._count;
      } else if (stat.status === 'PUBLISHED') {
        createdArticles.published = stat._count;
      }
    }

    let likes = 0,
      dislikes = 0;
    for (const stat of likeStats) {
      if (stat.type === 'LIKE') {
        likes = stat._count;
      } else if (stat.type === 'DISLIKE') {
        dislikes = stat._count;
      }
    }

    return {
      createdArticles,
      views: viewCount,
      reads: viewCount, // 暂时用浏览量代替
      likes,
      dislikes,
    };
  }

  /**
   * 获取未读提及数量
   */
  async getUnreadMentionCount(userId: string): Promise<number> {
    return this.prisma.userMention.count({
      where: {
        mentionedUserId: userId,
        readAt: null,
      },
    });
  }
}
