import prisma from '@/tools/prisma'
// 导入导出 Part 1: 
// ===== 【必须】从 BaseActionFun 导入并 re-export，照抄不要改 =====
import {
  UnauthorizedError,
  ForbiddenError,
  authStorage,
  parseTokenBase,
  runWithAuth,
  signToken,
  hashPassword,
  withResult,
} from '@/@base/BaseActionFun'

export {
  UnauthorizedError,
  ForbiddenError,
  runWithAuth,
  authStorage,
  signToken,
  hashPassword,
  withResult,
}
// ===== 【必须】导入导出结束 =====

// 导入导出 Part 2: 
// 从action_utils.type导入 AuthContext + **所有**定义的枚举类(Enums Definitions) 并re-export
import {
  UserRole,
  type AuthContext,
} from './action_utils.type'

export { UserRole } // 【必须】重新导出导出 re-export 已被定义的枚举类(Enums Definitions)
export type { AuthContext }
// 导入导出 Part 2 end

// ===== 内部方法 =====

/**
 * تحليل الرمز المميز (JWT Token) والتحقق من المستخدم في قاعدة البيانات
 * التحليل: يعتمد على جدول account_user لأن UserRole.ADMIN متوافق مع platform_user_role
 */
export async function parseToken(token: string): Promise<AuthContext | null> {
  const payload = await parseTokenBase(token)
  if (!payload) return null
  
  // التحقق من وجود المستخدم في جدول account_user
  const user = await prisma.account_user.findUnique({
    where: { id: payload.userId },
    select: {
      id: true,
      account: true,
      email: true,
      role: true,
    },
  })

  if (!user) return null

  return {
    userId: user.id,
    account: user.account,
    email: user.email,
    role: user.role as unknown as UserRole,
  }
}

// ===== 公共 API =====

/**
 * غلاف يتطلب تسجيل الدخول إجبارياً
 */
export function requireAuth() {
  return <TArgs extends any[], TReturn>(
    fn: (...args: TArgs) => Promise<TReturn>
  ) => {
    return async (...args: TArgs): Promise<TReturn> => {
      const ctx = authStorage.getStore() as AuthContext | undefined
      if (!ctx) throw new UnauthorizedError()
      return fn(...args)
    }
  }
}

/**
 * غلاف يتطلب دوراً وظيفياً محدداً
 */
export function requireRole(
  roles: UserRole | UserRole[] | string | string[]
) {
  return <TArgs extends any[], TReturn>(
    fn: (...args: TArgs) => Promise<TReturn>
  ) => {
    return async (...args: TArgs): Promise<TReturn> => {
      const ctx = authStorage.getStore() as AuthContext | undefined
      if (!ctx) throw new UnauthorizedError()

      const allowedRoles = Array.isArray(roles) ? roles : [roles]
      if (!allowedRoles.map(String).includes(String(ctx.role))) {
        throw new ForbiddenError()
      }

      return fn(...args)
    }
  }
}

/**
 * الحصول على سياق المصادقة للطلب الحالي
 */
export function getAuthContext(): AuthContext {
  const ctx = authStorage.getStore() as AuthContext | undefined
  if (!ctx) throw new UnauthorizedError()
  return ctx
}

/**
 * الحصول على معرف المستخدم الحالي
 */
export function getUserId(): string {
  return getAuthContext().userId
}

/**
 * الحصول على دور المستخدم الحالي
 */
export function getRole(): UserRole {
  return getAuthContext().role
}

/**
 * محاولة الحصول على سياق المصادقة (بدون رمي خطأ)
 */
export function tryGetAuthContext(): AuthContext | null {
  return (authStorage.getStore() as AuthContext | undefined) ?? null
}