/**
 * M2 协同备课 - Block 级评论数据访问层
 *
 * 评论挂载到 Block 级别，支持嵌套回复（parentCommentId）与解决状态（resolved）。
 * 实时多人编辑部分（Yjs/Liveblocks）需要单独的 WebSocket 服务，本文件仅实现评论 CRUD。
 */
import "server-only";
import { db } from "@/shared/db";
import { lessonPlanComments } from "@/shared/db/schema";
import { and, eq, asc, isNull } from "drizzle-orm";

/** 评论记录 */
export interface LessonPlanComment {
  id: string;
  planId: string;
  blockId: string;
  content: string;
  authorId: string;
  resolved: boolean;
  parentCommentId?: string;
  createdAt: Date;
  updatedAt: Date;
}

/**
 * 查询课案的所有评论（含子回复）
 */
export async function getCommentsByPlanId(
  planId: string,
): Promise<LessonPlanComment[]> {
  const rows = await db
    .select()
    .from(lessonPlanComments)
    .where(eq(lessonPlanComments.planId, planId))
    .orderBy(asc(lessonPlanComments.createdAt));

  return rows.map(mapRowToComment);
}

/**
 * 查询特定 Block 的评论
 */
export async function getCommentsByBlockId(
  planId: string,
  blockId: string,
): Promise<LessonPlanComment[]> {
  const rows = await db
    .select()
    .from(lessonPlanComments)
    .where(
      and(
        eq(lessonPlanComments.planId, planId),
        eq(lessonPlanComments.blockId, blockId),
      ),
    )
    .orderBy(asc(lessonPlanComments.createdAt));

  return rows.map(mapRowToComment);
}

/**
 * 创建评论
 */
export async function createComment(
  input: {
    planId: string;
    blockId: string;
    content: string;
    parentCommentId?: string;
  },
  authorId: string,
): Promise<LessonPlanComment> {
  const [row] = await db.insert(lessonPlanComments).values({
    planId: input.planId,
    blockId: input.blockId,
    content: input.content,
    authorId,
    resolved: false,
    parentCommentId: input.parentCommentId,
  });
  const insertedId = row.insertId;
  const all = await getCommentsByPlanId(input.planId);
  const created = all.find((c) => c.id === String(insertedId));
  if (!created) throw new Error("COMMENT_CREATE_FAILED");
  return created;
}

/**
 * 更新评论内容
 */
export async function updateCommentContent(
  commentId: string,
  content: string,
): Promise<void> {
  await db
    .update(lessonPlanComments)
    .set({ content, updatedAt: new Date() })
    .where(eq(lessonPlanComments.id, commentId));
}

/**
 * 切换评论解决状态
 */
export async function toggleCommentResolved(
  commentId: string,
): Promise<void> {
  const rows = await db
    .select({ resolved: lessonPlanComments.resolved })
    .from(lessonPlanComments)
    .where(eq(lessonPlanComments.id, commentId))
    .limit(1);
  if (rows.length === 0) return;
  const newResolved = !rows[0]!.resolved;
  await db
    .update(lessonPlanComments)
    .set({ resolved: newResolved, updatedAt: new Date() })
    .where(eq(lessonPlanComments.id, commentId));
}

/**
 * 删除评论（递归删除子回复）
 */
export async function deleteComment(commentId: string): Promise<void> {
  // 先删除所有子回复
  const children = await db
    .select({ id: lessonPlanComments.id })
    .from(lessonPlanComments)
    .where(eq(lessonPlanComments.parentCommentId, commentId));
  for (const child of children) {
    await deleteComment(child.id);
  }
  await db
    .delete(lessonPlanComments)
    .where(eq(lessonPlanComments.id, commentId));
}

/**
 * 统计课案未解决评论数
 */
export async function countUnresolvedComments(planId: string): Promise<number> {
  const rows = await db
    .select({ id: lessonPlanComments.id })
    .from(lessonPlanComments)
    .where(
      and(
        eq(lessonPlanComments.planId, planId),
        eq(lessonPlanComments.resolved, false),
        isNull(lessonPlanComments.parentCommentId),
      ),
    );
  return rows.length;
}

function mapRowToComment(
  row: typeof lessonPlanComments.$inferSelect,
): LessonPlanComment {
  return {
    id: row.id,
    planId: row.planId,
    blockId: row.blockId,
    content: row.content,
    authorId: row.authorId,
    resolved: row.resolved,
    parentCommentId: row.parentCommentId ?? undefined,
    createdAt: row.createdAt,
    updatedAt: row.updatedAt,
  };
}
