'use client';

import { useEffect, useMemo, useState } from 'react';

type UserRecord = {
  id: string;
  name: string;
  email: string;
  status: 'invited' | 'active' | 'inactive' | 'suspended';
  roleId: string | null;
  roleName: string;
  createdAt: string;
  updatedAt: string;
  lastLoginAt: string | null;
  emailVerifiedAt: string | null;
};

type RoleOption = {
  id: string;
  name: string;
};

type Props = {
  labels: Record<string, string>;
  initialUsers: UserRecord[];
  initialTotal: number;
  initialPage: number;
  initialPageSize: number;
  initialTotalPages: number;
  availableRoles: RoleOption[];
};

type PanelMode = 'create' | 'edit' | null;

function formatLastSeen(value: string | null, status: UserRecord['status'], labels: Record<string, string>) {
  if (status === 'invited') return labels.pendingInvite;
  if (!value) return labels.never;

  const diffMs = Date.now() - new Date(value).getTime();
  const minutes = Math.max(1, Math.floor(diffMs / 60000));
  if (minutes < 60) return labels.justNow;
  const hours = Math.floor(minutes / 60);
  if (hours < 24) return `${hours} ${hours === 1 ? labels.hourAgo : labels.hoursAgo}`;
  const days = Math.floor(hours / 24);
  return `${days} ${days === 1 ? labels.dayAgo : labels.daysAgo}`;
}

function formatStatusLabel(status: UserRecord['status'], labels: Record<string, string>) {
  switch (status) {
    case 'active':
      return labels.active;
    case 'invited':
      return labels.invited;
    case 'inactive':
      return labels.inactive;
    case 'suspended':
      return labels.suspended;
  }
}

function getStatusTone(status: UserRecord['status']) {
  switch (status) {
    case 'active':
      return 'success';
    case 'invited':
      return 'warning';
    case 'suspended':
      return 'error';
    case 'inactive':
      return 'muted';
  }
}

function getRoleTone(roleName: string) {
  const normalized = roleName.toLowerCase();
  if (normalized.includes('admin')) return 'admin';
  if (normalized.includes('editor')) return 'editor';
  return 'agent';
}

function initials(name: string) {
  return name
    .split(/\s+/)
    .slice(0, 2)
    .map((part) => part[0]?.toUpperCase() || '')
    .join('');
}

function roleDescription(roleName: string, labels: Record<string, string>) {
  const normalized = roleName.toLowerCase();
  if (normalized.includes('admin')) return labels.roleAdminDesc;
  if (normalized.includes('editor')) return labels.roleEditorDesc;
  if (normalized.includes('agent')) return labels.roleAgentDesc;
  return labels.roleDefaultDesc;
}

export function UsersManagementBoard({
  labels,
  initialUsers,
  initialTotal,
  initialPage,
  initialPageSize,
  initialTotalPages,
  availableRoles,
}: Props) {
  const [users, setUsers] = useState(initialUsers);
  const [total, setTotal] = useState(initialTotal);
  const [page, setPage] = useState(initialPage);
  const [pageSize] = useState(initialPageSize);
  const [totalPages, setTotalPages] = useState(initialTotalPages);
  const [search, setSearch] = useState('');
  const [debouncedSearch, setDebouncedSearch] = useState('');
  const [statusFilter, setStatusFilter] = useState('all');
  const [roleFilter, setRoleFilter] = useState('all');
  const [showFilters, setShowFilters] = useState(false);
  const [panelMode, setPanelMode] = useState<PanelMode>(null);
  const [editingUserId, setEditingUserId] = useState<string | null>(null);
  const [feedback, setFeedback] = useState('');
  const [inviteName, setInviteName] = useState('');
  const [inviteEmail, setInviteEmail] = useState('');
  const [inviteRoleId, setInviteRoleId] = useState(availableRoles[0]?.id || '');
  const [editName, setEditName] = useState('');
  const [editEmail, setEditEmail] = useState('');
  const [editRoleId, setEditRoleId] = useState('');
  const [editStatus, setEditStatus] = useState<UserRecord['status']>('active');
  const [isSaving, setIsSaving] = useState(false);
  const [isLoading, setIsLoading] = useState(false);

  const editingUser = useMemo(
    () => users.find((user) => user.id === editingUserId) ?? null,
    [editingUserId, users],
  );

  const stats = useMemo(() => {
    const totalUsers = total;
    const pendingInvites = users.filter((user) => user.status === 'invited').length;
    const activeRecently = users.filter((user) => {
      if (!user.lastLoginAt) return false;
      return Date.now() - new Date(user.lastLoginAt).getTime() <= 24 * 60 * 60 * 1000;
    }).length;
    return { totalUsers, pendingInvites, activeRecently };
  }, [total, users]);

  const visibleRoles = useMemo(() => {
    const base = availableRoles.map((role) => role.name);
    return base.slice(0, 3);
  }, [availableRoles]);

  useEffect(() => {
    const timeout = window.setTimeout(() => {
      setDebouncedSearch(search.trim());
      setPage(1);
    }, 250);
    return () => window.clearTimeout(timeout);
  }, [search]);

  useEffect(() => {
    const controller = new AbortController();

    async function loadUsers() {
      try {
        setIsLoading(true);
        const params = new URLSearchParams();
        params.set('page', String(page));
        params.set('limit', String(pageSize));
        if (debouncedSearch) params.set('search', debouncedSearch);
        if (statusFilter !== 'all') params.set('status', statusFilter);
        if (roleFilter !== 'all') params.set('roleId', roleFilter);

        const response = await fetch(`/api/users?${params.toString()}`, {
          credentials: 'include',
          signal: controller.signal,
          cache: 'no-store',
        });
        const payload = await response.json();
        if (!response.ok) {
          setFeedback(payload.message || labels.failedLoad);
          return;
        }

        setUsers(payload.items);
        setTotal(payload.total);
        setTotalPages(payload.totalPages);
      } catch (error) {
        if ((error as Error).name !== 'AbortError') {
          setFeedback(labels.failedLoad);
        }
      } finally {
        setIsLoading(false);
      }
    }

    loadUsers();
    return () => controller.abort();
  }, [debouncedSearch, page, pageSize, roleFilter, statusFilter]);

  function closePanel() {
    setPanelMode(null);
    setEditingUserId(null);
  }

  function openCreatePanel() {
    setPanelMode('create');
    setEditingUserId(null);
    setFeedback('');
  }

  function beginEdit(user: UserRecord) {
    setPanelMode('edit');
    setEditingUserId(user.id);
    setEditName(user.name);
    setEditEmail(user.email);
    setEditRoleId(user.roleId || '');
    setEditStatus(user.status);
    setFeedback('');
  }

  async function submitInvite() {
    setIsSaving(true);
    try {
      const response = await fetch('/api/users', {
        method: 'POST',
        credentials: 'include',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({
          name: inviteName,
          email: inviteEmail,
          roleId: inviteRoleId || undefined,
        }),
      });
      const payload = await response.json();
      if (!response.ok) {
        setFeedback(payload.message || labels.failedInvite);
        return;
      }

      setFeedback(
        payload.emailSent
          ? `${labels.invitationSent} ${payload.email}.`
          : `${labels.userInvitedNoEmail} ${payload.invitationUrl}`,
      );
      setInviteName('');
      setInviteEmail('');
      setInviteRoleId(availableRoles[0]?.id || '');
      closePanel();
      setPage(1);
      setDebouncedSearch('');
      setSearch('');
    } finally {
      setIsSaving(false);
    }
  }

  async function submitEdit() {
    if (!editingUser) return;
    setIsSaving(true);
    try {
      const response = await fetch(`/api/users/${editingUser.id}`, {
        method: 'PATCH',
        credentials: 'include',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({
          name: editName,
          email: editEmail,
          roleId: editRoleId || undefined,
          status: editStatus,
        }),
      });
      const payload = await response.json();
      if (!response.ok) {
        setFeedback(payload.message || labels.failedUpdate);
        return;
      }

      setUsers((current) =>
        current.map((user) =>
          user.id === payload.id
            ? {
                ...user,
                name: payload.name,
                email: payload.email,
                status: payload.status,
                roleId: payload.roleId,
                roleName: payload.roleName,
                lastLoginAt: payload.lastLoginAt,
                emailVerifiedAt: payload.emailVerifiedAt,
              }
            : user,
        ),
      );
      setFeedback(`${payload.email} ${labels.userUpdated}`);
      closePanel();
    } finally {
      setIsSaving(false);
    }
  }

  async function resendInvite(user: UserRecord) {
    setIsSaving(true);
    try {
      const response = await fetch('/api/users', {
        method: 'POST',
        credentials: 'include',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({
          name: user.name,
          email: user.email,
          roleId: user.roleId || undefined,
        }),
      });
      const payload = await response.json();
      if (!response.ok) {
        setFeedback(payload.message || labels.failedResend);
        return;
      }

      setFeedback(
        payload.emailSent
          ? `${labels.invitationResent} ${payload.email}.`
          : `${labels.inviteRefreshedNoEmail} ${payload.invitationUrl}`,
      );
    } finally {
      setIsSaving(false);
    }
  }

  function resetFilters() {
    setSearch('');
    setDebouncedSearch('');
    setStatusFilter('all');
    setRoleFilter('all');
    setPage(1);
  }

  function exportUsers() {
    const params = new URLSearchParams();
    if (debouncedSearch) params.set('search', debouncedSearch);
    if (statusFilter !== 'all') params.set('status', statusFilter);
    if (roleFilter !== 'all') params.set('roleId', roleFilter);
    window.location.href = `/api/users/export${params.size ? `?${params.toString()}` : ''}`;
  }

  return (
    <section className="users-board">
      <section className="page-header split users-page-header">
        <div>
          <p className="page-eyebrow">{labels.users}</p>
          <h1 className="page-heading">{labels.title}</h1>
          <p className="page-copy">{labels.description}</p>
        </div>
        <div className="header-actions">
          <button type="button" className="users-hero-button" onClick={openCreatePanel}>
            <span className="material-symbols-outlined">person_add</span>
            {labels.createUser}
          </button>
        </div>
      </section>

      <section className="users-stats-grid">
        <article className="users-stat-card">
          <div>
            <p className="users-stat-label">{labels.totalUsers}</p>
            <h3>{stats.totalUsers}</h3>
            <p className="users-stat-copy">
              <span className="material-symbols-outlined">trending_up</span>
              {labels.directoryAccounts}
            </p>
          </div>
          <div className="users-stat-icon tone-primary">
            <span className="material-symbols-outlined">group</span>
          </div>
        </article>

        <article className="users-stat-card">
          <div>
            <p className="users-stat-label">{labels.pendingInvites}</p>
            <h3>{stats.pendingInvites}</h3>
            <p className="users-stat-copy is-warning">
              <span className="material-symbols-outlined">schedule</span>
              {labels.awaitingResponse}
            </p>
          </div>
          <div className="users-stat-icon tone-secondary">
            <span className="material-symbols-outlined">mail</span>
          </div>
        </article>

        <article className="users-stat-card is-accent">
          <div className="users-stat-content">
            <p className="users-stat-label">{labels.activeSessions}</p>
            <h3>{stats.activeRecently}</h3>
            <p className="users-stat-copy">{labels.currentActivity}</p>
          </div>
          <div className="users-stat-icon tone-contrast">
            <span className="material-symbols-outlined">bolt</span>
          </div>
          <div className="users-stat-glow" />
        </article>
      </section>

      {panelMode === 'create' ? (
        <section className="users-panel-layout">
          <div className="users-create-main">
            <article className="users-form-card create">
              <div className="users-form-head create">
                <div>
                  <p className="card-kicker">{labels.settingsTeam}</p>
                  <h2>{labels.addMember}</h2>
                  <p>{labels.inviteCopy}</p>
                </div>
              </div>

              <div className="users-create-section">
                <h3>
                  <span className="material-symbols-outlined">person_add</span>
                  {labels.profileInformation}
                </h3>
                <div className="users-form-grid">
                  <label className="users-form-field">
                    <span>{labels.fullName}</span>
                    <input value={inviteName} onChange={(event) => setInviteName(event.target.value)} placeholder={labels.fullNamePlaceholder} />
                  </label>
                  <label className="users-form-field">
                    <span>{labels.emailAddress}</span>
                    <input value={inviteEmail} onChange={(event) => setInviteEmail(event.target.value)} placeholder="sarah.j@enterprise.com" />
                  </label>
                  <label className="users-form-field">
                    <span>{labels.phoneOptional}</span>
                    <input placeholder={labels.phonePlaceholder} disabled />
                  </label>
                  <label className="users-form-field">
                    <span>{labels.roleSelection}</span>
                    <select value={inviteRoleId} onChange={(event) => setInviteRoleId(event.target.value)}>
                      {availableRoles.map((role) => (
                        <option key={role.id} value={role.id}>
                          {role.name}
                        </option>
                      ))}
                    </select>
                  </label>
                </div>
              </div>

              <div className="users-footer-actions">
                <button type="button" className="secondary-button" onClick={closePanel}>
                  {labels.cancel}
                </button>
                <button type="button" className="users-hero-button" onClick={submitInvite} disabled={isSaving}>
                  <span className="material-symbols-outlined">send</span>
                  {isSaving ? labels.creating : labels.createUser}
                </button>
              </div>
            </article>
          </div>

          <aside className="users-create-side">
            <article className="users-summary-card">
              <h4>{labels.summary}</h4>
              <div className="users-summary-list">
                <div>
                  <span>{labels.role}</span>
                  <strong>
                    {availableRoles.find((role) => role.id === inviteRoleId)?.name || labels.supportAgent}
                  </strong>
                </div>
                <div>
                  <span>{labels.status}</span>
                  <strong>{labels.draftInvitation}</strong>
                </div>
                <p>
                  {labels.inviteSummary}
                </p>
              </div>
            </article>

            <article className="users-illustration-card">
              <div className="users-illustration-art" />
              <div className="users-illustration-copy">
                <h5>{labels.secureOnboarding}</h5>
                <p>{labels.secureOnboardingCopy}</p>
              </div>
            </article>
          </aside>
        </section>
      ) : null}

      {panelMode === 'edit' && editingUser ? (
        <section className="users-edit-layout">
          <aside className="users-edit-side">
            <article className="users-profile-card">
              <div className="users-profile-avatar">{initials(editingUser.name)}</div>
              <h3>{editingUser.name}</h3>
              <p>{editingUser.email}</p>
              <div className="users-profile-meta">
                <div>
                  <div>
                    <p>{labels.status}</p>
                    <strong className={`tone-${getStatusTone(editingUser.status)}`}>
                      {formatStatusLabel(editingUser.status, labels)}
                    </strong>
                  </div>
                </div>
                <div>
                  <p>{labels.lastActive}</p>
                  <strong>{formatLastSeen(editingUser.lastLoginAt, editingUser.status, labels)}</strong>
                </div>
              </div>
            </article>

            <article className="users-security-card">
              <h4>{labels.securityActions}</h4>
              <button
                type="button"
                className="users-toolbar-button full"
                onClick={() => resendInvite(editingUser)}
                disabled={isSaving}
              >
                <span className="material-symbols-outlined">lock_reset</span>
                {labels.sendPasswordReset}
              </button>
            </article>
          </aside>

          <div className="users-edit-main">
            <article className="users-form-card edit">
              <div className="users-form-head edit">
                <div>
                  <p className="card-kicker">{labels.editUser}</p>
                  <h2>{labels.updateAccess}</h2>
                  <p>{labels.updateAccessCopy}</p>
                </div>
                <span className={`users-panel-badge tone-${getStatusTone(editingUser.status)}`}>
                  {formatStatusLabel(editingUser.status, labels)}
                </span>
              </div>

              <div className="users-form-grid">
                <label className="users-form-field">
                  <span>{labels.fullName}</span>
                  <input value={editName} onChange={(event) => setEditName(event.target.value)} />
                </label>
                <label className="users-form-field">
                  <span>{labels.emailAddress}</span>
                  <input value={editEmail} onChange={(event) => setEditEmail(event.target.value)} />
                </label>
                <label className="users-form-field">
                  <span>{labels.role}</span>
                  <select value={editRoleId} onChange={(event) => setEditRoleId(event.target.value)}>
                    <option value="">{labels.unassigned}</option>
                    {availableRoles.map((role) => (
                      <option key={role.id} value={role.id}>
                        {role.name}
                      </option>
                    ))}
                  </select>
                </label>
                <label className="users-form-field">
                  <span>{labels.status}</span>
                  <select value={editStatus} onChange={(event) => setEditStatus(event.target.value as UserRecord['status'])}>
                    <option value="invited">{labels.invited}</option>
                    <option value="active">{labels.active}</option>
                    <option value="inactive">{labels.inactive}</option>
                    <option value="suspended">{labels.suspended}</option>
                  </select>
                </label>
              </div>

              <div className="users-edit-meta">
                <div>
                  <strong>{editingUser.emailVerifiedAt ? labels.verified : labels.pendingVerification}</strong>
                  <span>{labels.emailVerification}</span>
                </div>
                <div>
                  <strong>{formatLastSeen(editingUser.lastLoginAt, editingUser.status, labels)}</strong>
                  <span>{labels.lastActivity}</span>
                </div>
              </div>

              <div className="users-footer-actions">
                <button type="button" className="secondary-button" onClick={closePanel}>
                  {labels.cancel}
                </button>
                <button type="button" className="users-hero-button" onClick={submitEdit} disabled={isSaving}>
                  <span className="material-symbols-outlined">save</span>
                  {isSaving ? labels.saving : labels.saveChanges}
                </button>
              </div>
            </article>

            <article className="users-danger-card">
              <div className="users-danger-icon">
                <span className="material-symbols-outlined">warning</span>
              </div>
              <div>
                <h4>{labels.dangerZone}</h4>
                <p>{labels.dangerCopy}</p>
                <button type="button" disabled>
                  {labels.deleteUser}
                </button>
              </div>
            </article>
          </div>
        </section>
      ) : null}

      {feedback ? <p className="users-feedback">{feedback}</p> : null}

      <section className="users-table-shell">
        <div className="users-table-toolbar">
          <h4>{labels.teamMembers}</h4>
          <div className="users-toolbar-actions">
            <button type="button" className="users-toolbar-button large" onClick={() => setShowFilters((current) => !current)}>
              <span className="material-symbols-outlined">filter_list</span>
              {labels.filter}
            </button>
            <button type="button" className="users-toolbar-button large" onClick={exportUsers}>
              <span className="material-symbols-outlined">download</span>
              {labels.export}
            </button>
          </div>
        </div>

        {showFilters ? (
          <div className="users-filters-panel">
            <label className="users-filter-field">
              <span>{labels.searchMembers}</span>
              <input value={search} onChange={(event) => setSearch(event.target.value)} placeholder={labels.searchPlaceholder} />
            </label>
            <label className="users-filter-field">
              <span>{labels.status}</span>
              <select value={statusFilter} onChange={(event) => {
                setStatusFilter(event.target.value);
                setPage(1);
              }}>
                <option value="all">{labels.allStatuses}</option>
                <option value="invited">{labels.invited}</option>
                <option value="active">{labels.active}</option>
                <option value="inactive">{labels.inactive}</option>
                <option value="suspended">{labels.suspended}</option>
              </select>
            </label>
            <label className="users-filter-field">
              <span>{labels.role}</span>
              <select value={roleFilter} onChange={(event) => {
                setRoleFilter(event.target.value);
                setPage(1);
              }}>
                <option value="all">{labels.allRoles}</option>
                {availableRoles.map((role) => (
                  <option key={role.id} value={role.id}>
                    {role.name}
                  </option>
                ))}
              </select>
            </label>
            <div className="users-filter-actions">
              <button type="button" className="secondary-button" onClick={resetFilters}>
                {labels.reset}
              </button>
            </div>
          </div>
        ) : null}

        <div className="users-table-wrap">
          <table className="users-table">
            <thead>
              <tr>
                <th>{labels.nameEmail}</th>
                <th>{labels.role}</th>
                <th>{labels.lastActive}</th>
                <th>{labels.status}</th>
                <th className="align-right">{labels.actions}</th>
              </tr>
            </thead>
            <tbody>
              {users.map((user) => (
                <tr key={user.id}>
                  <td>
                    <div className="users-identity">
                      <div className={`users-avatar tone-${getRoleTone(user.roleName)}`}>{initials(user.name)}</div>
                      <div>
                        <p>{user.name}</p>
                        <span>{user.email}</span>
                      </div>
                    </div>
                  </td>
                  <td>
                    <span className={`users-role-pill tone-${getRoleTone(user.roleName)}`}>
                      {user.roleName.toUpperCase()}
                    </span>
                  </td>
                  <td className="users-muted">{formatLastSeen(user.lastLoginAt, user.status, labels)}</td>
                  <td>
                    <div className="users-status">
                      <span className={`users-status-dot tone-${getStatusTone(user.status)}`} />
                      <span>{formatStatusLabel(user.status, labels)}</span>
                    </div>
                  </td>
                  <td>
                    <div className="users-actions">
                      {user.status === 'invited' ? (
                        <button type="button" onClick={() => resendInvite(user)} title={labels.resendInvite}>
                          <span className="material-symbols-outlined">mail</span>
                        </button>
                      ) : null}
                      <button type="button" onClick={() => beginEdit(user)} title={labels.editUser}>
                        <span className="material-symbols-outlined">edit</span>
                      </button>
                    </div>
                  </td>
                </tr>
              ))}
              {users.length === 0 ? (
                <tr>
                  <td colSpan={5} className="users-empty-state">
                    {labels.noUsers}
                  </td>
                </tr>
              ) : null}
            </tbody>
          </table>
        </div>

        <div className="users-pagination">
          <p>
            {labels.showing} {users.length === 0 ? 0 : (page - 1) * pageSize + 1} {labels.to} {(page - 1) * pageSize + users.length} {labels.of} {total} {labels.teamMembersLower}
          </p>
          <div className="users-pagination-buttons">
            <button type="button" onClick={() => setPage((current) => Math.max(1, current - 1))} disabled={page <= 1}>
              <span className="material-symbols-outlined">chevron_left</span>
            </button>
            {Array.from({ length: totalPages }, (_, index) => index + 1)
              .slice(Math.max(0, page - 2), Math.max(0, page - 2) + 3)
              .map((pageNumber) => (
                <button
                  key={pageNumber}
                  type="button"
                  className={pageNumber === page ? 'is-active' : ''}
                  onClick={() => setPage(pageNumber)}
                >
                  {pageNumber}
                </button>
              ))}
            <button type="button" onClick={() => setPage((current) => Math.min(totalPages, current + 1))} disabled={page >= totalPages}>
              <span className="material-symbols-outlined">chevron_right</span>
            </button>
          </div>
        </div>
        {isLoading ? <div className="users-loading-bar" /> : null}
      </section>

      <section className="users-role-overview">
        <div>
          <h5>{labels.rolePermissions}</h5>
          <p>{labels.rolePermissionsCopy}</p>
        </div>
        <div className="users-role-cards">
          {visibleRoles.map((roleName) => (
            <article key={roleName} className="users-role-card">
              <div className={`users-role-card-head tone-${getRoleTone(roleName)}`}>
                <span className="material-symbols-outlined">
                  {getRoleTone(roleName) === 'admin'
                    ? 'verified_user'
                    : getRoleTone(roleName) === 'editor'
                      ? 'edit_note'
                      : 'support_agent'}
                </span>
                <span>{roleName.toUpperCase()}</span>
              </div>
              <p>{roleDescription(roleName, labels)}</p>
            </article>
          ))}
        </div>
      </section>
    </section>
  );
}
