import { redirect } from "next/navigation";

import { Badge } from "@/components/ui/badge";
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
import { Table } from "@/components/ui/table";
import { getCurrentAuthContext, toPublicAccount } from "@/modules/core/server/auth";
import { getRoleDefinitions, hasPermission } from "@/modules/core/server/permissions";
import {
  listSettingsAccounts,
  listSettingsJoinRequests,
  listSettingsMemberships,
  listSettingsOrganizations,
} from "@/modules/core/server/settings";
import { ROLE_LABELS } from "@/modules/core/types";
import type { RoleId } from "@/modules/core/types";
import { TablePagination, TableToolbar } from "@/modules/settings/components/TableToolbar";
import { UserAccountActions, UserManagementClient } from "@/modules/settings/components/UserManagementClient";
import { getPage, getPageCount, getSearchParam, paginate, type SearchParams } from "@/modules/settings/lib/pagination";
import { UserAvatar } from "@/modules/shared/components/UserAvatar";
import { getWorkspaceHref } from "@/modules/shared/lib/workspace-routing";

type UsersPageProps = {
  searchParams?: Promise<SearchParams>;
};

function formatRoleLabel(role: string): string {
  if (role in ROLE_LABELS) {
    return ROLE_LABELS[role as RoleId];
  }

  return role;
}

export default async function UsersPage({ searchParams }: UsersPageProps): Promise<React.ReactElement> {
  const context = await getCurrentAuthContext();
  if (!context) {
    redirect("/login");
  }

  if (!hasPermission(context.permissions, "account:read")) {
    redirect(getWorkspaceHref(context.organization?.slug, "/dashboard"));
  }

  const pagePath = getWorkspaceHref(context.organization?.slug, "/settings/users");
  const params = (await searchParams) ?? {};
  const query = getSearchParam(params, "q");
  const page = getPage(params);
  const canReadAllAccounts = Boolean(context.account.platformRoleId);
  const organizationScopeId = canReadAllAccounts ? undefined : context.organization?.id;
  const [organizations, accountsData, memberships, joinRequests, roles] = await Promise.all([
    listSettingsOrganizations(organizationScopeId ? { organizationId: organizationScopeId } : {}),
    listSettingsAccounts(organizationScopeId ? { organizationId: organizationScopeId } : {}),
    listSettingsMemberships(organizationScopeId ? { organizationId: organizationScopeId } : {}),
    listSettingsJoinRequests(organizationScopeId ? { organizationId: organizationScopeId } : {}),
    getRoleDefinitions(context.organization?.id),
  ]);
  const roleById = new Map(roles.map((role) => [role.id, role]));
  const organizationById = new Map(organizations.map((organization) => [organization.id, organization]));
  const accounts = accountsData.map((account) => {
    const membership = context.organization?.id
      ? memberships.find(
          (item) => item.accountId === account.id && item.organizationId === context.organization?.id && item.status === "active",
        )
      : memberships.find((item) => item.accountId === account.id && item.status === "active");
    const organization = membership ? organizationById.get(membership.organizationId) : undefined;
    const platformRole = account.platformRoleId ? roleById.get(account.platformRoleId) : undefined;

    return toPublicAccount(account, platformRole?.key ?? membership?.roleKey, organization);
  });
  const normalizedQuery = query.trim().toLowerCase();
  const filteredAccounts = accounts.filter((account) =>
    [account.name, account.email, account.status, String(account.role), account.organization ?? ""]
      .join(" ")
      .toLowerCase()
      .includes(normalizedQuery),
  );
  const pageCount = getPageCount(filteredAccounts.length);
  const visibleAccounts = paginate(filteredAccounts, page);

  return (
    <div className="flex flex-col gap-5">
      <UserManagementClient
        canManageAccounts={hasPermission(context.permissions, "account:manage")}
        organizations={organizations}
        roles={roles}
        joinRequests={joinRequests}
      />

      <Card>
        <CardHeader>
          <CardTitle>账号列表</CardTitle>
        </CardHeader>
        <CardContent className="p-0">
          <TableToolbar
            pathname={pagePath}
            query={query}
            searchPlaceholder="搜索姓名、邮箱、角色、状态"
            total={filteredAccounts.length}
          />
          <div className="overflow-x-auto">
            <Table className="w-full min-w-[920px] text-sm">
              <Table.Header className="bg-secondary text-left text-xs text-muted-foreground">
                <Table.Row>
                  <Table.Head className="px-4 py-3 font-medium">账号</Table.Head>
                  <Table.Head className="px-4 py-3 font-medium">角色</Table.Head>
                  <Table.Head className="px-4 py-3 font-medium">机构</Table.Head>
                  <Table.Head className="px-4 py-3 font-medium">状态</Table.Head>
                  <Table.Head className="px-4 py-3 text-right font-medium">创建时间</Table.Head>
                  <Table.Head className="px-4 py-3 text-right font-medium">操作</Table.Head>
                </Table.Row>
              </Table.Header>
              <Table.Body className="divide-y bg-card">
                {visibleAccounts.map((account) => (
                  <Table.Row className="table-row-enter hover:bg-secondary/45" key={account.id}>
                    <Table.Cell className="px-4 py-3">
                      <div className="flex items-center gap-3">
                        <UserAvatar avatarUrl={account.avatarUrl} name={account.name} size="sm" />
                        <div className="min-w-0">
                          <p className="truncate font-medium">{account.name}</p>
                          <p className="truncate text-xs text-muted-foreground">{account.email}</p>
                        </div>
                      </div>
                    </Table.Cell>
                    <Table.Cell className="px-4 py-3">{formatRoleLabel(account.role)}</Table.Cell>
                    <Table.Cell className="px-4 py-3 text-muted-foreground">{account.organization ?? "-"}</Table.Cell>
                    <Table.Cell className="px-4 py-3">
                      <Badge variant={account.status === "active" ? "success" : account.status === "pending" ? "warning" : "danger"}>
                        {account.status === "active" ? "启用" : account.status === "pending" ? "待审批" : "停用"}
                      </Badge>
                    </Table.Cell>
                    <Table.Cell className="px-4 py-3 text-right text-muted-foreground">
                      {new Date(account.createdAt).toLocaleString("zh-CN")}
                    </Table.Cell>
                    <Table.Cell className="px-4 py-3">
                      <UserAccountActions
                        account={account}
                        currentAccountId={context.account.id}
                        organizations={organizations}
                        roles={roles}
                      />
                    </Table.Cell>
                  </Table.Row>
                ))}
                {visibleAccounts.length === 0 ? (
                  <Table.Row>
                    <Table.Cell className="px-4 py-8 text-center text-muted-foreground" colSpan={6}>
                      暂无匹配账号
                    </Table.Cell>
                  </Table.Row>
                ) : null}
              </Table.Body>
            </Table>
          </div>
          <TablePagination
            page={Math.min(page, pageCount)}
            pageCount={pageCount}
            pathname={pagePath}
            query={query}
            total={filteredAccounts.length}
          />
        </CardContent>
      </Card>
    </div>
  );
}
