/**
 * 钉钉SDK工具类
 * 
 * 提供钉钉环境检测、免登授权码获取等功能
 */

// 钉钉JSAPI类型声明
declare global {
  interface Window {
    dd?: {
      env: {
        platform: 'notInDingTalk' | 'android' | 'ios' | 'pc'
      }
      ready: (callback: () => void) => void
      error: (callback: (err: any) => void) => void
      runtime: {
        permission: {
          requestAuthCode: (options: {
            corpId: string
            onSuccess: (result: { code: string }) => void
            onFail: (err: any) => void
          }) => void
        }
      }
      biz: {
        navigation: {
          setTitle: (options: { title: string }) => void
        }
      }
    }
  }
}

/**
 * 钉钉配置接口
 */
export interface DingtalkConfig {
  enabled: boolean
  corp_id: string | null
  agent_id: string | null
}

/**
 * 检测是否在钉钉环境中
 */
export function isDingtalkEnv(): boolean {
  if (typeof window === 'undefined') {
    console.log('[钉钉检测] window 不存在')
    return false
  }
  
  // 首先通过 User-Agent 检测
  const ua = navigator.userAgent.toLowerCase()
  const isDingTalkUA = ua.includes('dingtalk') || ua.includes('aliapp')
  console.log('[钉钉检测] UA检测:', isDingTalkUA, 'UA:', ua.substring(0, 100))
  
  if (!window.dd) {
    console.log('[钉钉检测] window.dd 不存在，但UA检测为:', isDingTalkUA)
    return isDingTalkUA // 如果 UA 显示是钉钉但 SDK 还没加载，也返回 true
  }
  
  const platform = window.dd.env?.platform
  console.log('[钉钉检测] dd.env.platform:', platform)
  
  return platform !== 'notInDingTalk'
}

/**
 * 获取钉钉平台类型
 */
export function getDingtalkPlatform(): string {
  if (!window.dd) return 'notInDingTalk'
  return window.dd.env.platform
}

/**
 * 等待钉钉SDK就绪（带超时）
 */
export function waitDingtalkReady(timeout: number = 5000): Promise<void> {
  return new Promise((resolve, reject) => {
    if (!window.dd) {
      reject(new Error('钉钉SDK未加载'))
      return
    }
    
    let resolved = false
    
    // 超时处理
    const timer = setTimeout(() => {
      if (!resolved) {
        resolved = true
        console.warn('钉钉SDK就绪超时，尝试继续执行')
        resolve() // 超时后也尝试继续，可能SDK已经就绪
      }
    }, timeout)
    
    window.dd.ready(() => {
      if (!resolved) {
        resolved = true
        clearTimeout(timer)
        console.log('钉钉SDK就绪')
        resolve()
      }
    })
    
    window.dd.error((err) => {
      if (!resolved) {
        resolved = true
        clearTimeout(timer)
        console.error('钉钉SDK错误:', err)
        reject(err)
      }
    })
  })
}

/**
 * 获取钉钉免登授权码
 * 
 * @param corpId 企业CorpId
 * @returns 免登授权码
 */
export function getAuthCode(corpId: string): Promise<string> {
  return new Promise((resolve, reject) => {
    if (!window.dd) {
      reject(new Error('钉钉SDK未加载'))
      return
    }
    
    if (!isDingtalkEnv()) {
      reject(new Error('当前不在钉钉环境中'))
      return
    }
    
    window.dd.runtime.permission.requestAuthCode({
      corpId: corpId,
      onSuccess: (result) => {
        resolve(result.code)
      },
      onFail: (err) => {
        console.error('获取钉钉授权码失败:', err)
        reject(new Error(err.message || '获取授权码失败'))
      }
    })
  })
}

/**
 * 设置钉钉页面标题
 */
export function setDingtalkTitle(title: string): void {
  if (!window.dd || !isDingtalkEnv()) return
  
  try {
    window.dd.biz.navigation.setTitle({ title })
  } catch (e) {
    console.warn('设置钉钉标题失败:', e)
  }
}

/**
 * 加载钉钉JSAPI SDK
 * 
 * 动态加载钉钉SDK脚本
 */
export function loadDingtalkSDK(): Promise<void> {
  return new Promise((resolve, reject) => {
    // 如果已经加载过，直接返回
    if (window.dd) {
      resolve()
      return
    }
    
    const script = document.createElement('script')
    script.src = 'https://g.alicdn.com/dingding/dingtalk-jsapi/3.0.12/dingtalk.open.js'
    script.async = true
    
    script.onload = () => {
      console.log('钉钉SDK加载成功')
      resolve()
    }
    
    script.onerror = () => {
      reject(new Error('钉钉SDK加载失败'))
    }
    
    document.head.appendChild(script)
  })
}

/**
 * 钉钉免密登录完整流程
 * 
 * @param corpId 企业CorpId
 * @param loginApi 登录API函数
 * @returns 登录结果
 */
export async function dingtalkAutoLogin(
  corpId: string,
  loginApi: (code: string) => Promise<any>
): Promise<any> {
  // 1. 检测钉钉环境
  if (!isDingtalkEnv()) {
    throw new Error('当前不在钉钉环境中，无法使用免密登录')
  }
  
  // 2. 等待SDK就绪
  await waitDingtalkReady()
  
  // 3. 获取授权码
  const code = await getAuthCode(corpId)
  
  // 4. 调用登录API
  const result = await loginApi(code)
  
  return result
}

export default {
  isDingtalkEnv,
  getDingtalkPlatform,
  waitDingtalkReady,
  getAuthCode,
  setDingtalkTitle,
  loadDingtalkSDK,
  dingtalkAutoLogin
}
