const database = require('../config/database'); const DEFAULT_AUTH_CONFIG = { authBaseUrl: '', dingtalkEnabled: false, dingtalkAppKey: '', dingtalkAppSecret: '', dingtalkSyncRootDeptId: 1, googleEnabled: false, googleClientId: '', googleClientSecret: '', }; const PUBLIC_AUTH_CONFIG_CACHE_TTL_MS = Math.max( Number(process.env.PUBLIC_AUTH_CONFIG_CACHE_TTL_SECONDS) || 300, 30 ) * 1000; let publicAuthConfigCache = null; let publicAuthConfigCacheExpiresAt = 0; function normalizeBoolean(value) { return value === true || value === 1 || value === '1'; } function mapRowToConfig(row) { if (!row) { return { ...DEFAULT_AUTH_CONFIG }; } return { id: row.id, authBaseUrl: row.auth_base_url || '', dingtalkEnabled: normalizeBoolean(row.dingtalk_enabled), dingtalkAppKey: row.dingtalk_app_key || '', dingtalkAppSecret: row.dingtalk_app_secret || '', dingtalkSyncRootDeptId: Number(row.dingtalk_sync_root_dept_id || 1), googleEnabled: normalizeBoolean(row.google_enabled), googleClientId: row.google_client_id || '', googleClientSecret: row.google_client_secret || '', }; } async function getAuthConfig() { const rows = await database.local.query( `SELECT id, auth_base_url, dingtalk_enabled, dingtalk_app_key, dingtalk_app_secret, dingtalk_sync_root_dept_id, google_enabled, google_client_id, google_client_secret FROM auth_configs ORDER BY id ASC LIMIT 1` ); return mapRowToConfig(rows[0]); } async function getPublicAuthConfig() { const now = Date.now(); if (publicAuthConfigCache && publicAuthConfigCacheExpiresAt > now) { return publicAuthConfigCache; } let config; try { config = await getAuthConfig(); } catch (error) { if (publicAuthConfigCache) { return publicAuthConfigCache; } throw error; } const publicConfig = { authBaseUrl: config.authBaseUrl, dingtalkEnabled: config.dingtalkEnabled && Boolean(config.dingtalkAppKey && config.dingtalkAppSecret), googleEnabled: config.googleEnabled && Boolean(config.googleClientId && config.googleClientSecret), }; publicAuthConfigCache = publicConfig; publicAuthConfigCacheExpiresAt = now + PUBLIC_AUTH_CONFIG_CACHE_TTL_MS; return publicConfig; } async function saveAuthConfig(input) { const current = await getAuthConfig(); publicAuthConfigCache = null; publicAuthConfigCacheExpiresAt = 0; const payload = { auth_base_url: typeof input.authBaseUrl === 'string' ? input.authBaseUrl.trim() : current.authBaseUrl, dingtalk_enabled: input.dingtalkEnabled === undefined ? (current.dingtalkEnabled ? 1 : 0) : (input.dingtalkEnabled ? 1 : 0), dingtalk_app_key: typeof input.dingtalkAppKey === 'string' ? input.dingtalkAppKey.trim() : current.dingtalkAppKey, dingtalk_app_secret: typeof input.dingtalkAppSecret === 'string' ? input.dingtalkAppSecret.trim() : current.dingtalkAppSecret, dingtalk_sync_root_dept_id: input.dingtalkSyncRootDeptId === undefined ? current.dingtalkSyncRootDeptId : Number(input.dingtalkSyncRootDeptId || 1), google_enabled: input.googleEnabled === undefined ? (current.googleEnabled ? 1 : 0) : (input.googleEnabled ? 1 : 0), google_client_id: typeof input.googleClientId === 'string' ? input.googleClientId.trim() : current.googleClientId, google_client_secret: typeof input.googleClientSecret === 'string' ? input.googleClientSecret.trim() : current.googleClientSecret, }; if (current.id) { await database.local.update('auth_configs', current.id, payload); return getAuthConfig(); } await database.local.insert('auth_configs', payload); return getAuthConfig(); } module.exports = { DEFAULT_AUTH_CONFIG, getAuthConfig, getPublicAuthConfig, saveAuthConfig, };