import { t as __exportAll } from "./rolldown-runtime-Cbj13DAv.js";
import { g as resolveOAuthPath } from "./paths-By0XjHBk.js";
import { h as resolveUserPath } from "./utils-CTPsqyE_.js";
import { t as createSubsystemLogger } from "./subsystem-CHbO_DkH.js";
import { t as formatCliCommand } from "./command-format-BzjsXBTi.js";
import { a as findNormalizedProviderValue, i as findNormalizedProviderKey, u as normalizeProviderId, x as getProviderAdapter } from "./model-selection-7wdmO-Iw.js";
import { n as normalizeSecretInput } from "./normalize-secret-input-DjGU5EXe.js";
import { t as withFileLock } from "./file-lock-BVUYnlQv.js";
import { n as saveJsonFile, t as loadJsonFile } from "./json-file-CNp4GTiH.js";
import { t as resolveSymiAgentDir } from "./agent-paths-BbZSGrUA.js";
import { createHash, randomBytes } from "node:crypto";
import path from "node:path";
import fs from "node:fs";
import { execFileSync } from "node:child_process";
import { getOAuthApiKey, getOAuthProviders } from "@mariozechner/pi-ai";

//#region src/agents/auth-profiles/constants.ts
const AUTH_STORE_VERSION = 1;
const AUTH_PROFILE_FILENAME = "auth-profiles.json";
const LEGACY_AUTH_FILENAME = "auth.json";
const CLAUDE_CLI_PROFILE_ID = "anthropic:claude-cli";
const CODEX_CLI_PROFILE_ID = "openai-codex:codex-cli";
const QWEN_CLI_PROFILE_ID = "qwen-portal:qwen-cli";
const MINIMAX_CLI_PROFILE_ID = "minimax-portal:minimax-cli";
const AUTH_STORE_LOCK_OPTIONS = {
	retries: {
		retries: 10,
		factor: 2,
		minTimeout: 100,
		maxTimeout: 1e4,
		randomize: true
	},
	stale: 3e4
};
const EXTERNAL_CLI_SYNC_TTL_MS = 900 * 1e3;
const EXTERNAL_CLI_NEAR_EXPIRY_MS = 600 * 1e3;
const log$1 = createSubsystemLogger("agents/auth-profiles");

//#endregion
//#region src/agents/auth-profiles/display.ts
function resolveAuthProfileDisplayLabel(params) {
	const { cfg, store, profileId } = params;
	const profile = store.profiles[profileId];
	const email = cfg?.auth?.profiles?.[profileId]?.email?.trim() || (profile && "email" in profile ? profile.email?.trim() : void 0);
	if (email) return `${profileId} (${email})`;
	return profileId;
}

//#endregion
//#region src/agents/cli-credentials.ts
const log = createSubsystemLogger("agents/auth-profiles");
const QWEN_CLI_CREDENTIALS_RELATIVE_PATH = ".qwen/oauth_creds.json";
const MINIMAX_CLI_CREDENTIALS_RELATIVE_PATH = ".minimax/oauth_creds.json";
let qwenCliCache = null;
let minimaxCliCache = null;
function resolveQwenCliCredentialsPath(homeDir) {
	const baseDir = homeDir ?? resolveUserPath("~");
	return path.join(baseDir, QWEN_CLI_CREDENTIALS_RELATIVE_PATH);
}
function resolveMiniMaxCliCredentialsPath(homeDir) {
	const baseDir = homeDir ?? resolveUserPath("~");
	return path.join(baseDir, MINIMAX_CLI_CREDENTIALS_RELATIVE_PATH);
}
function readQwenCliCredentials(options) {
	return readPortalCliOauthCredentials(resolveQwenCliCredentialsPath(options?.homeDir), "qwen-portal");
}
function readPortalCliOauthCredentials(credPath, provider) {
	const raw = loadJsonFile(credPath);
	if (!raw || typeof raw !== "object") return null;
	const data = raw;
	const accessToken = data.access_token;
	const refreshToken = data.refresh_token;
	const expiresAt = data.expiry_date;
	if (typeof accessToken !== "string" || !accessToken) return null;
	if (typeof refreshToken !== "string" || !refreshToken) return null;
	if (typeof expiresAt !== "number" || !Number.isFinite(expiresAt)) return null;
	return {
		type: "oauth",
		provider,
		access: accessToken,
		refresh: refreshToken,
		expires: expiresAt
	};
}
function readMiniMaxCliCredentials(options) {
	return readPortalCliOauthCredentials(resolveMiniMaxCliCredentialsPath(options?.homeDir), "minimax-portal");
}
function readQwenCliCredentialsCached(options) {
	const ttlMs = options?.ttlMs ?? 0;
	const now = Date.now();
	const cacheKey = resolveQwenCliCredentialsPath(options?.homeDir);
	if (ttlMs > 0 && qwenCliCache && qwenCliCache.cacheKey === cacheKey && now - qwenCliCache.readAt < ttlMs) return qwenCliCache.value;
	const value = readQwenCliCredentials({ homeDir: options?.homeDir });
	if (ttlMs > 0) qwenCliCache = {
		value,
		readAt: now,
		cacheKey
	};
	return value;
}
function readMiniMaxCliCredentialsCached(options) {
	const ttlMs = options?.ttlMs ?? 0;
	const now = Date.now();
	const cacheKey = resolveMiniMaxCliCredentialsPath(options?.homeDir);
	if (ttlMs > 0 && minimaxCliCache && minimaxCliCache.cacheKey === cacheKey && now - minimaxCliCache.readAt < ttlMs) return minimaxCliCache.value;
	const value = readMiniMaxCliCredentials({ homeDir: options?.homeDir });
	if (ttlMs > 0) minimaxCliCache = {
		value,
		readAt: now,
		cacheKey
	};
	return value;
}

//#endregion
//#region src/agents/auth-profiles/external-cli-sync.ts
function shallowEqualOAuthCredentials(a, b) {
	if (!a) return false;
	if (a.type !== "oauth") return false;
	return a.provider === b.provider && a.access === b.access && a.refresh === b.refresh && a.expires === b.expires && a.email === b.email && a.enterpriseUrl === b.enterpriseUrl && a.projectId === b.projectId && a.accountId === b.accountId;
}
function isExternalProfileFresh(cred, now) {
	if (!cred) return false;
	if (cred.type !== "oauth" && cred.type !== "token") return false;
	if (cred.provider !== "qwen-portal" && cred.provider !== "minimax-portal") return false;
	if (typeof cred.expires !== "number") return true;
	return cred.expires > now + EXTERNAL_CLI_NEAR_EXPIRY_MS;
}
/** Sync external CLI credentials into the store for a given provider. */
function syncExternalCliCredentialsForProvider(store, profileId, provider, readCredentials, now) {
	const existing = store.profiles[profileId];
	const creds = !existing || existing.provider !== provider || !isExternalProfileFresh(existing, now) ? readCredentials() : null;
	if (!creds) return false;
	const existingOAuth = existing?.type === "oauth" ? existing : void 0;
	if ((!existingOAuth || existingOAuth.provider !== provider || existingOAuth.expires <= now || creds.expires > existingOAuth.expires) && !shallowEqualOAuthCredentials(existingOAuth, creds)) {
		store.profiles[profileId] = creds;
		log$1.info(`synced ${provider} credentials from external cli`, {
			profileId,
			expires: new Date(creds.expires).toISOString()
		});
		return true;
	}
	return false;
}
/**
* Sync OAuth credentials from external CLI tools (Qwen Code CLI, MiniMax CLI) into the store.
*
* Returns true if any credentials were updated.
*/
function syncExternalCliCredentials(store) {
	let mutated = false;
	const now = Date.now();
	const existingQwen = store.profiles[QWEN_CLI_PROFILE_ID];
	const qwenCreds = !existingQwen || existingQwen.provider !== "qwen-portal" || !isExternalProfileFresh(existingQwen, now) ? readQwenCliCredentialsCached({ ttlMs: EXTERNAL_CLI_SYNC_TTL_MS }) : null;
	if (qwenCreds) {
		const existing = store.profiles[QWEN_CLI_PROFILE_ID];
		const existingOAuth = existing?.type === "oauth" ? existing : void 0;
		if ((!existingOAuth || existingOAuth.provider !== "qwen-portal" || existingOAuth.expires <= now || qwenCreds.expires > existingOAuth.expires) && !shallowEqualOAuthCredentials(existingOAuth, qwenCreds)) {
			store.profiles[QWEN_CLI_PROFILE_ID] = qwenCreds;
			mutated = true;
			log$1.info("synced qwen credentials from qwen cli", {
				profileId: QWEN_CLI_PROFILE_ID,
				expires: new Date(qwenCreds.expires).toISOString()
			});
		}
	}
	if (syncExternalCliCredentialsForProvider(store, MINIMAX_CLI_PROFILE_ID, "minimax-portal", () => readMiniMaxCliCredentialsCached({ ttlMs: EXTERNAL_CLI_SYNC_TTL_MS }), now)) mutated = true;
	return mutated;
}

//#endregion
//#region src/agents/auth-profiles/paths.ts
function resolveAuthStorePath(agentDir) {
	const resolved = resolveUserPath(agentDir ?? resolveSymiAgentDir());
	return path.join(resolved, AUTH_PROFILE_FILENAME);
}
function resolveLegacyAuthStorePath(agentDir) {
	const resolved = resolveUserPath(agentDir ?? resolveSymiAgentDir());
	return path.join(resolved, LEGACY_AUTH_FILENAME);
}
function resolveAuthStorePathForDisplay(agentDir) {
	const pathname = resolveAuthStorePath(agentDir);
	return pathname.startsWith("~") ? pathname : resolveUserPath(pathname);
}
function ensureAuthStoreFile(pathname) {
	if (fs.existsSync(pathname)) return;
	saveJsonFile(pathname, {
		version: AUTH_STORE_VERSION,
		profiles: {}
	});
}

//#endregion
//#region src/agents/auth-profiles/store.ts
async function updateAuthProfileStoreWithLock(params) {
	const authPath = resolveAuthStorePath(params.agentDir);
	ensureAuthStoreFile(authPath);
	try {
		return await withFileLock(authPath, AUTH_STORE_LOCK_OPTIONS, async () => {
			const store = ensureAuthProfileStore(params.agentDir);
			if (params.updater(store)) saveAuthProfileStore(store, params.agentDir);
			return store;
		});
	} catch {
		return null;
	}
}
function coerceLegacyStore(raw) {
	if (!raw || typeof raw !== "object") return null;
	const record = raw;
	if ("profiles" in record) return null;
	const entries = {};
	for (const [key, value] of Object.entries(record)) {
		if (!value || typeof value !== "object") continue;
		const typed = value;
		if (typed.type !== "api_key" && typed.type !== "oauth" && typed.type !== "token") continue;
		entries[key] = {
			...typed,
			provider: String(typed.provider ?? key)
		};
	}
	return Object.keys(entries).length > 0 ? entries : null;
}
function coerceAuthStore(raw) {
	if (!raw || typeof raw !== "object") return null;
	const record = raw;
	if (!record.profiles || typeof record.profiles !== "object") return null;
	const profiles = record.profiles;
	const normalized = {};
	for (const [key, value] of Object.entries(profiles)) {
		if (!value || typeof value !== "object") continue;
		const typed = value;
		if (typed.type !== "api_key" && typed.type !== "oauth" && typed.type !== "token") continue;
		if (!typed.provider) continue;
		normalized[key] = typed;
	}
	const order = record.order && typeof record.order === "object" ? Object.entries(record.order).reduce((acc, [provider, value]) => {
		if (!Array.isArray(value)) return acc;
		const list = value.map((entry) => typeof entry === "string" ? entry.trim() : "").filter(Boolean);
		if (list.length === 0) return acc;
		acc[provider] = list;
		return acc;
	}, {}) : void 0;
	return {
		version: Number(record.version ?? AUTH_STORE_VERSION),
		profiles: normalized,
		order,
		lastGood: record.lastGood && typeof record.lastGood === "object" ? record.lastGood : void 0,
		usageStats: record.usageStats && typeof record.usageStats === "object" ? record.usageStats : void 0
	};
}
function mergeRecord(base, override) {
	if (!base && !override) return;
	if (!base) return { ...override };
	if (!override) return { ...base };
	return {
		...base,
		...override
	};
}
function mergeAuthProfileStores(base, override) {
	if (Object.keys(override.profiles).length === 0 && !override.order && !override.lastGood && !override.usageStats) return base;
	return {
		version: Math.max(base.version, override.version ?? base.version),
		profiles: {
			...base.profiles,
			...override.profiles
		},
		order: mergeRecord(base.order, override.order),
		lastGood: mergeRecord(base.lastGood, override.lastGood),
		usageStats: mergeRecord(base.usageStats, override.usageStats)
	};
}
function mergeOAuthFileIntoStore(store) {
	const oauthRaw = loadJsonFile(resolveOAuthPath());
	if (!oauthRaw || typeof oauthRaw !== "object") return false;
	const oauthEntries = oauthRaw;
	let mutated = false;
	for (const [provider, creds] of Object.entries(oauthEntries)) {
		if (!creds || typeof creds !== "object") continue;
		const profileId = `${provider}:default`;
		if (store.profiles[profileId]) continue;
		store.profiles[profileId] = {
			type: "oauth",
			provider,
			...creds
		};
		mutated = true;
	}
	return mutated;
}
function applyLegacyStore(store, legacy) {
	for (const [provider, cred] of Object.entries(legacy)) {
		const profileId = `${provider}:default`;
		if (cred.type === "api_key") {
			store.profiles[profileId] = {
				type: "api_key",
				provider: String(cred.provider ?? provider),
				key: cred.key,
				...cred.email ? { email: cred.email } : {}
			};
			continue;
		}
		if (cred.type === "token") {
			store.profiles[profileId] = {
				type: "token",
				provider: String(cred.provider ?? provider),
				token: cred.token,
				...typeof cred.expires === "number" ? { expires: cred.expires } : {},
				...cred.email ? { email: cred.email } : {}
			};
			continue;
		}
		store.profiles[profileId] = {
			type: "oauth",
			provider: String(cred.provider ?? provider),
			access: cred.access,
			refresh: cred.refresh,
			expires: cred.expires,
			...cred.enterpriseUrl ? { enterpriseUrl: cred.enterpriseUrl } : {},
			...cred.projectId ? { projectId: cred.projectId } : {},
			...cred.accountId ? { accountId: cred.accountId } : {},
			...cred.email ? { email: cred.email } : {}
		};
	}
}
function loadAuthProfileStore() {
	const authPath = resolveAuthStorePath();
	const asStore = coerceAuthStore(loadJsonFile(authPath));
	if (asStore) {
		if (syncExternalCliCredentials(asStore)) saveJsonFile(authPath, asStore);
		return asStore;
	}
	const legacy = coerceLegacyStore(loadJsonFile(resolveLegacyAuthStorePath()));
	if (legacy) {
		const store = {
			version: AUTH_STORE_VERSION,
			profiles: {}
		};
		applyLegacyStore(store, legacy);
		syncExternalCliCredentials(store);
		return store;
	}
	const store = {
		version: AUTH_STORE_VERSION,
		profiles: {}
	};
	syncExternalCliCredentials(store);
	return store;
}
function loadAuthProfileStoreForAgent(agentDir, _options) {
	const authPath = resolveAuthStorePath(agentDir);
	const asStore = coerceAuthStore(loadJsonFile(authPath));
	if (asStore) {
		if (syncExternalCliCredentials(asStore)) saveJsonFile(authPath, asStore);
		return asStore;
	}
	if (agentDir) {
		const mainStore = coerceAuthStore(loadJsonFile(resolveAuthStorePath()));
		if (mainStore && Object.keys(mainStore.profiles).length > 0) {
			saveJsonFile(authPath, mainStore);
			log$1.info("inherited auth-profiles from main agent", { agentDir });
			return mainStore;
		}
	}
	const legacy = coerceLegacyStore(loadJsonFile(resolveLegacyAuthStorePath(agentDir)));
	const store = {
		version: AUTH_STORE_VERSION,
		profiles: {}
	};
	if (legacy) applyLegacyStore(store, legacy);
	const mergedOAuth = mergeOAuthFileIntoStore(store);
	const syncedCli = syncExternalCliCredentials(store);
	const shouldWrite = legacy !== null || mergedOAuth || syncedCli;
	if (shouldWrite) saveJsonFile(authPath, store);
	if (shouldWrite && legacy !== null) {
		const legacyPath = resolveLegacyAuthStorePath(agentDir);
		try {
			fs.unlinkSync(legacyPath);
		} catch (err) {
			if (err?.code !== "ENOENT") log$1.warn("failed to delete legacy auth.json after migration", {
				err,
				legacyPath
			});
		}
	}
	return store;
}
function ensureAuthProfileStore(agentDir, options) {
	const store = loadAuthProfileStoreForAgent(agentDir, options);
	const authPath = resolveAuthStorePath(agentDir);
	const mainAuthPath = resolveAuthStorePath();
	if (!agentDir || authPath === mainAuthPath) return store;
	return mergeAuthProfileStores(loadAuthProfileStoreForAgent(void 0, options), store);
}
function saveAuthProfileStore(store, agentDir) {
	saveJsonFile(resolveAuthStorePath(agentDir), {
		version: AUTH_STORE_VERSION,
		profiles: store.profiles,
		order: store.order ?? void 0,
		lastGood: store.lastGood ?? void 0,
		usageStats: store.usageStats ?? void 0
	});
}

//#endregion
//#region src/agents/auth-profiles/profiles.ts
function dedupeProfileIds(profileIds) {
	return [...new Set(profileIds)];
}
async function setAuthProfileOrder(params) {
	const providerKey = normalizeProviderId(params.provider);
	const deduped = dedupeProfileIds(params.order && Array.isArray(params.order) ? params.order.map((entry) => String(entry).trim()).filter(Boolean) : []);
	return await updateAuthProfileStoreWithLock({
		agentDir: params.agentDir,
		updater: (store) => {
			store.order = store.order ?? {};
			if (deduped.length === 0) {
				if (!store.order[providerKey]) return false;
				delete store.order[providerKey];
				if (Object.keys(store.order).length === 0) store.order = void 0;
				return true;
			}
			store.order[providerKey] = deduped;
			return true;
		}
	});
}
function upsertAuthProfile(params) {
	const credential = params.credential.type === "api_key" ? {
		...params.credential,
		...typeof params.credential.key === "string" ? { key: normalizeSecretInput(params.credential.key) } : {}
	} : params.credential.type === "token" ? {
		...params.credential,
		token: normalizeSecretInput(params.credential.token)
	} : params.credential;
	const store = ensureAuthProfileStore(params.agentDir);
	store.profiles[params.profileId] = credential;
	saveAuthProfileStore(store, params.agentDir);
}
async function upsertAuthProfileWithLock(params) {
	return await updateAuthProfileStoreWithLock({
		agentDir: params.agentDir,
		updater: (store) => {
			store.profiles[params.profileId] = params.credential;
			return true;
		}
	});
}
function listProfilesForProvider(store, provider) {
	const providerKey = normalizeProviderId(provider);
	return Object.entries(store.profiles).filter(([, cred]) => normalizeProviderId(cred.provider) === providerKey).map(([id]) => id);
}
async function markAuthProfileGood(params) {
	const { store, provider, profileId, agentDir } = params;
	const updated = await updateAuthProfileStoreWithLock({
		agentDir,
		updater: (freshStore) => {
			const profile = freshStore.profiles[profileId];
			if (!profile || profile.provider !== provider) return false;
			freshStore.lastGood = {
				...freshStore.lastGood,
				[provider]: profileId
			};
			return true;
		}
	});
	if (updated) {
		store.lastGood = updated.lastGood;
		return;
	}
	const profile = store.profiles[profileId];
	if (!profile || profile.provider !== provider) return;
	store.lastGood = {
		...store.lastGood,
		[provider]: profileId
	};
	saveAuthProfileStore(store, agentDir);
}

//#endregion
//#region src/agents/auth-profiles/repair.ts
function getProfileSuffix(profileId) {
	const idx = profileId.indexOf(":");
	if (idx < 0) return "";
	return profileId.slice(idx + 1);
}
function isEmailLike(value) {
	const trimmed = value.trim();
	if (!trimmed) return false;
	return trimmed.includes("@") && trimmed.includes(".");
}
function suggestOAuthProfileIdForLegacyDefault(params) {
	const providerKey = normalizeProviderId(params.provider);
	if (getProfileSuffix(params.legacyProfileId) !== "default") return null;
	const legacyCfg = params.cfg?.auth?.profiles?.[params.legacyProfileId];
	if (legacyCfg && normalizeProviderId(legacyCfg.provider) === providerKey && legacyCfg.mode !== "oauth") return null;
	const oauthProfiles = listProfilesForProvider(params.store, providerKey).filter((id) => params.store.profiles[id]?.type === "oauth");
	if (oauthProfiles.length === 0) return null;
	const configuredEmail = legacyCfg?.email?.trim();
	if (configuredEmail) {
		const byEmail = oauthProfiles.find((id) => {
			const cred = params.store.profiles[id];
			if (!cred || cred.type !== "oauth") return false;
			return cred.email?.trim() === configuredEmail || id === `${providerKey}:${configuredEmail}`;
		});
		if (byEmail) return byEmail;
	}
	const lastGood = params.store.lastGood?.[providerKey] ?? params.store.lastGood?.[params.provider];
	if (lastGood && oauthProfiles.includes(lastGood)) return lastGood;
	const nonLegacy = oauthProfiles.filter((id) => id !== params.legacyProfileId);
	if (nonLegacy.length === 1) return nonLegacy[0] ?? null;
	const emailLike = nonLegacy.filter((id) => isEmailLike(getProfileSuffix(id)));
	if (emailLike.length === 1) return emailLike[0] ?? null;
	return null;
}
function repairOAuthProfileIdMismatch(params) {
	const legacyProfileId = params.legacyProfileId ?? `${normalizeProviderId(params.provider)}:default`;
	const legacyCfg = params.cfg.auth?.profiles?.[legacyProfileId];
	if (!legacyCfg) return {
		config: params.cfg,
		changes: [],
		migrated: false
	};
	if (legacyCfg.mode !== "oauth") return {
		config: params.cfg,
		changes: [],
		migrated: false
	};
	if (normalizeProviderId(legacyCfg.provider) !== normalizeProviderId(params.provider)) return {
		config: params.cfg,
		changes: [],
		migrated: false
	};
	const toProfileId = suggestOAuthProfileIdForLegacyDefault({
		cfg: params.cfg,
		store: params.store,
		provider: params.provider,
		legacyProfileId
	});
	if (!toProfileId || toProfileId === legacyProfileId) return {
		config: params.cfg,
		changes: [],
		migrated: false
	};
	const toCred = params.store.profiles[toProfileId];
	const toEmail = toCred?.type === "oauth" ? toCred.email?.trim() : void 0;
	const nextProfiles = { ...params.cfg.auth?.profiles };
	delete nextProfiles[legacyProfileId];
	nextProfiles[toProfileId] = {
		...legacyCfg,
		...toEmail ? { email: toEmail } : {}
	};
	const providerKey = normalizeProviderId(params.provider);
	const nextOrder = (() => {
		const order = params.cfg.auth?.order;
		if (!order) return;
		const resolvedKey = findNormalizedProviderKey(order, providerKey);
		if (!resolvedKey) return order;
		const existing = order[resolvedKey];
		if (!Array.isArray(existing)) return order;
		const deduped = dedupeProfileIds(existing.map((id) => id === legacyProfileId ? toProfileId : id).filter((id) => typeof id === "string" && id.trim().length > 0));
		return {
			...order,
			[resolvedKey]: deduped
		};
	})();
	return {
		config: {
			...params.cfg,
			auth: {
				...params.cfg.auth,
				profiles: nextProfiles,
				...nextOrder ? { order: nextOrder } : {}
			}
		},
		changes: [`Auth: migrate ${legacyProfileId} → ${toProfileId} (OAuth profile id)`],
		migrated: true,
		fromProfileId: legacyProfileId,
		toProfileId
	};
}

//#endregion
//#region src/agents/auth-profiles/doctor.ts
function formatAuthDoctorHint(params) {
	const providerKey = normalizeProviderId(params.provider);
	if (providerKey !== "anthropic") return "";
	const legacyProfileId = params.profileId ?? "anthropic:default";
	const suggested = suggestOAuthProfileIdForLegacyDefault({
		cfg: params.cfg,
		store: params.store,
		provider: providerKey,
		legacyProfileId
	});
	if (!suggested || suggested === legacyProfileId) return "";
	const storeOauthProfiles = listProfilesForProvider(params.store, providerKey).filter((id) => params.store.profiles[id]?.type === "oauth").join(", ");
	const cfgMode = params.cfg?.auth?.profiles?.[legacyProfileId]?.mode;
	const cfgProvider = params.cfg?.auth?.profiles?.[legacyProfileId]?.provider;
	return [
		"Doctor hint (for GitHub issue):",
		`- provider: ${providerKey}`,
		`- config: ${legacyProfileId}${cfgProvider || cfgMode ? ` (provider=${cfgProvider ?? "?"}, mode=${cfgMode ?? "?"})` : ""}`,
		`- auth store oauth profiles: ${storeOauthProfiles || "(none)"}`,
		`- suggested profile: ${suggested}`,
		`Fix: run "${formatCliCommand("symi doctor --yes")}"`
	].join("\n");
}

//#endregion
//#region src/providers/qwen-portal-oauth.ts
const QWEN_OAUTH_TOKEN_ENDPOINT = `https://chat.qwen.ai/api/v1/oauth2/token`;
const QWEN_OAUTH_CLIENT_ID = "f0304373b74a44d2b584a3fb70ca9e56";
async function refreshQwenPortalCredentials(credentials) {
	const refreshToken = credentials.refresh?.trim();
	if (!refreshToken) throw new Error("Qwen OAuth refresh token missing; re-authenticate.");
	const response = await fetch(QWEN_OAUTH_TOKEN_ENDPOINT, {
		method: "POST",
		headers: {
			"Content-Type": "application/x-www-form-urlencoded",
			Accept: "application/json"
		},
		body: new URLSearchParams({
			grant_type: "refresh_token",
			refresh_token: refreshToken,
			client_id: QWEN_OAUTH_CLIENT_ID
		})
	});
	if (!response.ok) {
		const text = await response.text();
		if (response.status === 400) throw new Error(`Qwen OAuth refresh token expired or invalid. Re-authenticate with \`${formatCliCommand("symi models auth login --provider qwen-portal")}\`.`);
		throw new Error(`Qwen OAuth refresh failed: ${text || response.statusText}`);
	}
	const payload = await response.json();
	const accessToken = payload.access_token?.trim();
	const newRefreshToken = payload.refresh_token?.trim();
	const expiresIn = payload.expires_in;
	if (!accessToken) throw new Error("Qwen OAuth refresh response missing access token.");
	if (typeof expiresIn !== "number" || !Number.isFinite(expiresIn) || expiresIn <= 0) throw new Error("Qwen OAuth refresh response missing or invalid expires_in.");
	return {
		...credentials,
		access: accessToken,
		refresh: newRefreshToken || refreshToken,
		expires: Date.now() + expiresIn * 1e3
	};
}

//#endregion
//#region src/agents/chutes-oauth.ts
const CHUTES_OAUTH_ISSUER = "https://api.chutes.ai";
const CHUTES_AUTHORIZE_ENDPOINT = `${CHUTES_OAUTH_ISSUER}/idp/authorize`;
const CHUTES_TOKEN_ENDPOINT = `${CHUTES_OAUTH_ISSUER}/idp/token`;
const CHUTES_USERINFO_ENDPOINT = `${CHUTES_OAUTH_ISSUER}/idp/userinfo`;
const DEFAULT_EXPIRES_BUFFER_MS = 300 * 1e3;
function generateChutesPkce() {
	const verifier = randomBytes(32).toString("hex");
	return {
		verifier,
		challenge: createHash("sha256").update(verifier).digest("base64url")
	};
}
function parseOAuthCallbackInput(input, expectedState) {
	const trimmed = input.trim();
	if (!trimmed) return { error: "No input provided" };
	let url;
	try {
		url = new URL(trimmed);
	} catch {
		if (!/\s/.test(trimmed) && !trimmed.includes("://") && !trimmed.includes("?") && !trimmed.includes("=")) return { error: "Paste the full redirect URL (must include code + state)." };
		const qs = trimmed.startsWith("?") ? trimmed : `?${trimmed}`;
		try {
			url = new URL(`http://localhost/${qs}`);
		} catch {
			return { error: "Paste the full redirect URL (must include code + state)." };
		}
	}
	const code = url.searchParams.get("code")?.trim();
	const state = url.searchParams.get("state")?.trim();
	if (!code) return { error: "Missing 'code' parameter in URL" };
	if (!state) return { error: "Missing 'state' parameter. Paste the full redirect URL." };
	if (state !== expectedState) return { error: "OAuth state mismatch - possible CSRF attack. Please retry login." };
	return {
		code,
		state
	};
}
function coerceExpiresAt(expiresInSeconds, now) {
	const value = now + Math.max(0, Math.floor(expiresInSeconds)) * 1e3 - DEFAULT_EXPIRES_BUFFER_MS;
	return Math.max(value, now + 3e4);
}
async function fetchChutesUserInfo(params) {
	const response = await (params.fetchFn ?? fetch)(CHUTES_USERINFO_ENDPOINT, { headers: { Authorization: `Bearer ${params.accessToken}` } });
	if (!response.ok) return null;
	const data = await response.json();
	if (!data || typeof data !== "object") return null;
	return data;
}
async function exchangeChutesCodeForTokens(params) {
	const fetchFn = params.fetchFn ?? fetch;
	const now = params.now ?? Date.now();
	const body = new URLSearchParams({
		grant_type: "authorization_code",
		client_id: params.app.clientId,
		code: params.code,
		redirect_uri: params.app.redirectUri,
		code_verifier: params.codeVerifier
	});
	if (params.app.clientSecret) body.set("client_secret", params.app.clientSecret);
	const response = await fetchFn(CHUTES_TOKEN_ENDPOINT, {
		method: "POST",
		headers: { "Content-Type": "application/x-www-form-urlencoded" },
		body
	});
	if (!response.ok) {
		const text = await response.text();
		throw new Error(`Chutes token exchange failed: ${text}`);
	}
	const data = await response.json();
	const access = data.access_token?.trim();
	const refresh = data.refresh_token?.trim();
	const expiresIn = data.expires_in ?? 0;
	if (!access) throw new Error("Chutes token exchange returned no access_token");
	if (!refresh) throw new Error("Chutes token exchange returned no refresh_token");
	const info = await fetchChutesUserInfo({
		accessToken: access,
		fetchFn
	});
	return {
		access,
		refresh,
		expires: coerceExpiresAt(expiresIn, now),
		email: info?.username,
		accountId: info?.sub,
		clientId: params.app.clientId
	};
}
async function refreshChutesTokens(params) {
	const fetchFn = params.fetchFn ?? fetch;
	const now = params.now ?? Date.now();
	const refreshToken = params.credential.refresh?.trim();
	if (!refreshToken) throw new Error("Chutes OAuth credential is missing refresh token");
	const clientId = params.credential.clientId?.trim() ?? process.env.CHUTES_CLIENT_ID?.trim();
	if (!clientId) throw new Error("Missing CHUTES_CLIENT_ID for Chutes OAuth refresh (set env var or re-auth).");
	const clientSecret = process.env.CHUTES_CLIENT_SECRET?.trim() || void 0;
	const body = new URLSearchParams({
		grant_type: "refresh_token",
		client_id: clientId,
		refresh_token: refreshToken
	});
	if (clientSecret) body.set("client_secret", clientSecret);
	const response = await fetchFn(CHUTES_TOKEN_ENDPOINT, {
		method: "POST",
		headers: { "Content-Type": "application/x-www-form-urlencoded" },
		body
	});
	if (!response.ok) {
		const text = await response.text();
		throw new Error(`Chutes token refresh failed: ${text}`);
	}
	const data = await response.json();
	const access = data.access_token?.trim();
	const newRefresh = data.refresh_token?.trim();
	const expiresIn = data.expires_in ?? 0;
	if (!access) throw new Error("Chutes token refresh returned no access_token");
	return {
		...params.credential,
		access,
		refresh: newRefresh || refreshToken,
		expires: coerceExpiresAt(expiresIn, now),
		clientId
	};
}

//#endregion
//#region src/agents/auth-profiles/oauth.ts
const OAUTH_PROVIDER_IDS = new Set(getOAuthProviders().map((provider) => provider.id));
const isOAuthProvider = (provider) => OAUTH_PROVIDER_IDS.has(provider);
const resolveOAuthProvider = (provider) => isOAuthProvider(provider) ? provider : null;
/** Bearer-token auth modes that are interchangeable (oauth tokens and raw tokens). */
const BEARER_AUTH_MODES = new Set(["oauth", "token"]);
const isCompatibleModeType = (mode, type) => {
	if (!mode || !type) return false;
	if (mode === type) return true;
	return BEARER_AUTH_MODES.has(mode) && BEARER_AUTH_MODES.has(type);
};
function isProfileConfigCompatible(params) {
	const profileConfig = params.cfg?.auth?.profiles?.[params.profileId];
	if (profileConfig && profileConfig.provider !== params.provider) return false;
	if (profileConfig && !isCompatibleModeType(profileConfig.mode, params.mode)) return false;
	return true;
}
function buildOAuthApiKey(provider, credentials) {
	return getProviderAdapter(provider).oauthNeedsProjectId?.() ?? false ? JSON.stringify({
		token: credentials.access,
		projectId: credentials.projectId
	}) : credentials.access;
}
function buildApiKeyProfileResult(params) {
	return {
		apiKey: params.apiKey,
		provider: params.provider,
		email: params.email
	};
}
function buildOAuthProfileResult(params) {
	return buildApiKeyProfileResult({
		apiKey: buildOAuthApiKey(params.provider, params.credentials),
		provider: params.provider,
		email: params.email
	});
}
function isExpiredCredential(expires) {
	return typeof expires === "number" && Number.isFinite(expires) && expires > 0 && Date.now() >= expires;
}
function adoptNewerMainOAuthCredential(params) {
	if (!params.agentDir) return null;
	try {
		const mainCred = ensureAuthProfileStore(void 0).profiles[params.profileId];
		if (mainCred?.type === "oauth" && mainCred.provider === params.cred.provider && Number.isFinite(mainCred.expires) && (!Number.isFinite(params.cred.expires) || mainCred.expires > params.cred.expires)) {
			params.store.profiles[params.profileId] = { ...mainCred };
			saveAuthProfileStore(params.store, params.agentDir);
			log$1.info("adopted newer OAuth credentials from main agent", {
				profileId: params.profileId,
				agentDir: params.agentDir,
				expires: new Date(mainCred.expires).toISOString()
			});
			return mainCred;
		}
	} catch (err) {
		log$1.debug("adoptNewerMainOAuthCredential failed", {
			profileId: params.profileId,
			error: err instanceof Error ? err.message : String(err)
		});
	}
	return null;
}
async function refreshOAuthTokenWithLock(params) {
	const authPath = resolveAuthStorePath(params.agentDir);
	ensureAuthStoreFile(authPath);
	return await withFileLock(authPath, AUTH_STORE_LOCK_OPTIONS, async () => {
		const store = ensureAuthProfileStore(params.agentDir);
		const cred = store.profiles[params.profileId];
		if (!cred || cred.type !== "oauth") return null;
		if (Date.now() < cred.expires) return {
			apiKey: buildOAuthApiKey(cred.provider, cred),
			newCredentials: cred
		};
		const oauthCreds = { [cred.provider]: cred };
		const result = String(cred.provider) === "chutes" ? await (async () => {
			const newCredentials = await refreshChutesTokens({ credential: cred });
			return {
				apiKey: newCredentials.access,
				newCredentials
			};
		})() : String(cred.provider) === "qwen-portal" ? await (async () => {
			const newCredentials = await refreshQwenPortalCredentials(cred);
			return {
				apiKey: newCredentials.access,
				newCredentials
			};
		})() : await (async () => {
			const oauthProvider = resolveOAuthProvider(cred.provider);
			if (!oauthProvider) return null;
			return await getOAuthApiKey(oauthProvider, oauthCreds);
		})();
		if (!result) return null;
		store.profiles[params.profileId] = {
			...cred,
			...result.newCredentials,
			type: "oauth"
		};
		saveAuthProfileStore(store, params.agentDir);
		return result;
	});
}
async function tryResolveOAuthProfile(params) {
	const { cfg, store, profileId } = params;
	const cred = store.profiles[profileId];
	if (!cred || cred.type !== "oauth") return null;
	if (!isProfileConfigCompatible({
		cfg,
		profileId,
		provider: cred.provider,
		mode: cred.type
	})) return null;
	if (Date.now() < cred.expires) return buildOAuthProfileResult({
		provider: cred.provider,
		credentials: cred,
		email: cred.email
	});
	const refreshed = await refreshOAuthTokenWithLock({
		profileId,
		agentDir: params.agentDir
	});
	if (!refreshed) return null;
	return buildApiKeyProfileResult({
		apiKey: refreshed.apiKey,
		provider: cred.provider,
		email: cred.email
	});
}
async function resolveApiKeyForProfile(params) {
	const { cfg, store, profileId } = params;
	const cred = store.profiles[profileId];
	if (!cred) return null;
	if (!isProfileConfigCompatible({
		cfg,
		profileId,
		provider: cred.provider,
		mode: cred.type,
		allowOAuthTokenCompatibility: true
	})) return null;
	if (cred.type === "api_key") {
		const key = cred.key?.trim();
		if (!key) return null;
		return buildApiKeyProfileResult({
			apiKey: key,
			provider: cred.provider,
			email: cred.email
		});
	}
	if (cred.type === "token") {
		const token = cred.token?.trim();
		if (!token) return null;
		if (isExpiredCredential(cred.expires)) return null;
		return buildApiKeyProfileResult({
			apiKey: token,
			provider: cred.provider,
			email: cred.email
		});
	}
	const oauthCred = adoptNewerMainOAuthCredential({
		store,
		profileId,
		agentDir: params.agentDir,
		cred
	}) ?? cred;
	if (Date.now() < oauthCred.expires) return buildOAuthProfileResult({
		provider: oauthCred.provider,
		credentials: oauthCred,
		email: oauthCred.email
	});
	try {
		const result = await refreshOAuthTokenWithLock({
			profileId,
			agentDir: params.agentDir
		});
		if (!result) return null;
		return buildApiKeyProfileResult({
			apiKey: result.apiKey,
			provider: cred.provider,
			email: cred.email
		});
	} catch (error) {
		const refreshedStore = ensureAuthProfileStore(params.agentDir);
		const refreshed = refreshedStore.profiles[profileId];
		if (refreshed?.type === "oauth" && Date.now() < refreshed.expires) return buildOAuthProfileResult({
			provider: refreshed.provider,
			credentials: refreshed,
			email: refreshed.email ?? cred.email
		});
		const fallbackProfileId = suggestOAuthProfileIdForLegacyDefault({
			cfg,
			store: refreshedStore,
			provider: cred.provider,
			legacyProfileId: profileId
		});
		if (fallbackProfileId && fallbackProfileId !== profileId) try {
			const fallbackResolved = await tryResolveOAuthProfile({
				cfg,
				store: refreshedStore,
				profileId: fallbackProfileId,
				agentDir: params.agentDir
			});
			if (fallbackResolved) return fallbackResolved;
		} catch {}
		if (params.agentDir) try {
			const mainCred = ensureAuthProfileStore(void 0).profiles[profileId];
			if (mainCred?.type === "oauth" && Date.now() < mainCred.expires) {
				refreshedStore.profiles[profileId] = { ...mainCred };
				saveAuthProfileStore(refreshedStore, params.agentDir);
				log$1.info("inherited fresh OAuth credentials from main agent", {
					profileId,
					agentDir: params.agentDir,
					expires: new Date(mainCred.expires).toISOString()
				});
				return buildOAuthProfileResult({
					provider: mainCred.provider,
					credentials: mainCred,
					email: mainCred.email
				});
			}
		} catch {}
		const message = error instanceof Error ? error.message : String(error);
		const hint = formatAuthDoctorHint({
			cfg,
			store: refreshedStore,
			provider: cred.provider,
			profileId
		});
		throw new Error(`OAuth token refresh failed for ${cred.provider}: ${message}. Please try again or re-authenticate.` + (hint ? `\n\n${hint}` : ""), { cause: error });
	}
}

//#endregion
//#region src/agents/auth-profiles/usage.ts
function resolveProfileUnusableUntil(stats) {
	const values = [stats.cooldownUntil, stats.disabledUntil].filter((value) => typeof value === "number").filter((value) => Number.isFinite(value) && value > 0);
	if (values.length === 0) return null;
	return Math.max(...values);
}
/**
* Check if a profile is currently in cooldown (due to rate limiting or errors).
*/
function isProfileInCooldown(store, profileId) {
	const stats = store.usageStats?.[profileId];
	if (!stats) return false;
	const unusableUntil = resolveProfileUnusableUntil(stats);
	return unusableUntil ? Date.now() < unusableUntil : false;
}
/**
* Return the soonest `unusableUntil` timestamp (ms epoch) among the given
* profiles, or `null` when no profile has a recorded cooldown. Note: the
* returned timestamp may be in the past if the cooldown has already expired.
*/
function getSoonestCooldownExpiry(store, profileIds) {
	let soonest = null;
	for (const id of profileIds) {
		const stats = store.usageStats?.[id];
		if (!stats) continue;
		const until = resolveProfileUnusableUntil(stats);
		if (typeof until !== "number" || !Number.isFinite(until) || until <= 0) continue;
		if (soonest === null || until < soonest) soonest = until;
	}
	return soonest;
}
/**
* Clear expired cooldowns from all profiles in the store.
*
* When `cooldownUntil` or `disabledUntil` has passed, the corresponding fields
* are removed and error counters are reset so the profile gets a fresh start
* (circuit-breaker half-open → closed). Without this, a stale `errorCount`
* causes the *next* transient failure to immediately escalate to a much longer
* cooldown — the root cause of profiles appearing "stuck" after rate limits.
*
* `cooldownUntil` and `disabledUntil` are handled independently: if a profile
* has both and only one has expired, only that field is cleared.
*
* Mutates the in-memory store; disk persistence happens lazily on the next
* store write (e.g. `markAuthProfileUsed` / `markAuthProfileFailure`), which
* matches the existing save pattern throughout the auth-profiles module.
*
* @returns `true` if any profile was modified.
*/
function clearExpiredCooldowns(store, now) {
	const usageStats = store.usageStats;
	if (!usageStats) return false;
	const ts = now ?? Date.now();
	let mutated = false;
	for (const [profileId, stats] of Object.entries(usageStats)) {
		if (!stats) continue;
		let profileMutated = false;
		const cooldownExpired = typeof stats.cooldownUntil === "number" && Number.isFinite(stats.cooldownUntil) && stats.cooldownUntil > 0 && ts >= stats.cooldownUntil;
		const disabledExpired = typeof stats.disabledUntil === "number" && Number.isFinite(stats.disabledUntil) && stats.disabledUntil > 0 && ts >= stats.disabledUntil;
		if (cooldownExpired) {
			stats.cooldownUntil = void 0;
			profileMutated = true;
		}
		if (disabledExpired) {
			stats.disabledUntil = void 0;
			stats.disabledReason = void 0;
			profileMutated = true;
		}
		if (profileMutated && !resolveProfileUnusableUntil(stats)) {
			stats.errorCount = 0;
			stats.failureCounts = void 0;
		}
		if (profileMutated) {
			usageStats[profileId] = stats;
			mutated = true;
		}
	}
	return mutated;
}
/**
* Mark a profile as successfully used. Resets error count and updates lastUsed.
* Uses store lock to avoid overwriting concurrent usage updates.
*/
async function markAuthProfileUsed(params) {
	const { store, profileId, agentDir } = params;
	const updated = await updateAuthProfileStoreWithLock({
		agentDir,
		updater: (freshStore) => {
			if (!freshStore.profiles[profileId]) return false;
			freshStore.usageStats = freshStore.usageStats ?? {};
			freshStore.usageStats[profileId] = {
				...freshStore.usageStats[profileId],
				lastUsed: Date.now(),
				errorCount: 0,
				cooldownUntil: void 0,
				disabledUntil: void 0,
				disabledReason: void 0,
				failureCounts: void 0
			};
			return true;
		}
	});
	if (updated) {
		store.usageStats = updated.usageStats;
		return;
	}
	if (!store.profiles[profileId]) return;
	store.usageStats = store.usageStats ?? {};
	store.usageStats[profileId] = {
		...store.usageStats[profileId],
		lastUsed: Date.now(),
		errorCount: 0,
		cooldownUntil: void 0,
		disabledUntil: void 0,
		disabledReason: void 0,
		failureCounts: void 0
	};
	saveAuthProfileStore(store, agentDir);
}
function calculateAuthProfileCooldownMs(errorCount) {
	const normalized = Math.max(1, errorCount);
	return Math.min(3600 * 1e3, 60 * 1e3 * 5 ** Math.min(normalized - 1, 3));
}
function resolveAuthCooldownConfig(params) {
	const defaults = {
		billingBackoffHours: 5,
		billingMaxHours: 24,
		failureWindowHours: 24
	};
	const resolveHours = (value, fallback) => typeof value === "number" && Number.isFinite(value) && value > 0 ? value : fallback;
	const cooldowns = params.cfg?.auth?.cooldowns;
	const billingBackoffHours = resolveHours((() => {
		const map = cooldowns?.billingBackoffHoursByProvider;
		if (!map) return;
		for (const [key, value] of Object.entries(map)) if (normalizeProviderId(key) === params.providerId) return value;
	})() ?? cooldowns?.billingBackoffHours, defaults.billingBackoffHours);
	const billingMaxHours = resolveHours(cooldowns?.billingMaxHours, defaults.billingMaxHours);
	const failureWindowHours = resolveHours(cooldowns?.failureWindowHours, defaults.failureWindowHours);
	return {
		billingBackoffMs: billingBackoffHours * 60 * 60 * 1e3,
		billingMaxMs: billingMaxHours * 60 * 60 * 1e3,
		failureWindowMs: failureWindowHours * 60 * 60 * 1e3
	};
}
function calculateAuthProfileBillingDisableMsWithConfig(params) {
	const normalized = Math.max(1, params.errorCount);
	const baseMs = Math.max(6e4, params.baseMs);
	const maxMs = Math.max(baseMs, params.maxMs);
	const raw = baseMs * 2 ** Math.min(normalized - 1, 10);
	return Math.min(maxMs, raw);
}
function resolveProfileUnusableUntilForDisplay(store, profileId) {
	const stats = store.usageStats?.[profileId];
	if (!stats) return null;
	return resolveProfileUnusableUntil(stats);
}
function computeNextProfileUsageStats(params) {
	const windowMs = params.cfgResolved.failureWindowMs;
	const windowExpired = typeof params.existing.lastFailureAt === "number" && params.existing.lastFailureAt > 0 && params.now - params.existing.lastFailureAt > windowMs;
	const nextErrorCount = (windowExpired ? 0 : params.existing.errorCount ?? 0) + 1;
	const failureCounts = windowExpired ? {} : { ...params.existing.failureCounts };
	failureCounts[params.reason] = (failureCounts[params.reason] ?? 0) + 1;
	const updatedStats = {
		...params.existing,
		errorCount: nextErrorCount,
		failureCounts,
		lastFailureAt: params.now
	};
	if (params.reason === "billing") {
		const backoffMs = calculateAuthProfileBillingDisableMsWithConfig({
			errorCount: failureCounts.billing ?? 1,
			baseMs: params.cfgResolved.billingBackoffMs,
			maxMs: params.cfgResolved.billingMaxMs
		});
		updatedStats.disabledUntil = params.now + backoffMs;
		updatedStats.disabledReason = "billing";
	} else {
		const backoffMs = calculateAuthProfileCooldownMs(nextErrorCount);
		updatedStats.cooldownUntil = params.now + backoffMs;
	}
	return updatedStats;
}
/**
* Mark a profile as failed for a specific reason. Billing failures are treated
* as "disabled" (longer backoff) vs the regular cooldown window.
*/
async function markAuthProfileFailure(params) {
	const { store, profileId, reason, agentDir, cfg } = params;
	const updated = await updateAuthProfileStoreWithLock({
		agentDir,
		updater: (freshStore) => {
			const profile = freshStore.profiles[profileId];
			if (!profile) return false;
			freshStore.usageStats = freshStore.usageStats ?? {};
			const existing = freshStore.usageStats[profileId] ?? {};
			const now = Date.now();
			const cfgResolved = resolveAuthCooldownConfig({
				cfg,
				providerId: normalizeProviderId(profile.provider)
			});
			freshStore.usageStats[profileId] = computeNextProfileUsageStats({
				existing,
				now,
				reason,
				cfgResolved
			});
			return true;
		}
	});
	if (updated) {
		store.usageStats = updated.usageStats;
		return;
	}
	if (!store.profiles[profileId]) return;
	store.usageStats = store.usageStats ?? {};
	const existing = store.usageStats[profileId] ?? {};
	const now = Date.now();
	const cfgResolved = resolveAuthCooldownConfig({
		cfg,
		providerId: normalizeProviderId(store.profiles[profileId]?.provider ?? "")
	});
	store.usageStats[profileId] = computeNextProfileUsageStats({
		existing,
		now,
		reason,
		cfgResolved
	});
	saveAuthProfileStore(store, agentDir);
}

//#endregion
//#region src/agents/auth-profiles/order.ts
function resolveAuthProfileOrder(params) {
	const { cfg, store, provider, preferredProfile } = params;
	const providerKey = normalizeProviderId(provider);
	const now = Date.now();
	clearExpiredCooldowns(store, now);
	const storedOrder = findNormalizedProviderValue(store.order, providerKey);
	const configuredOrder = findNormalizedProviderValue(cfg?.auth?.order, providerKey);
	const explicitOrder = storedOrder ?? configuredOrder;
	const explicitProfiles = cfg?.auth?.profiles ? Object.entries(cfg.auth.profiles).filter(([, profile]) => normalizeProviderId(profile.provider) === providerKey).map(([profileId]) => profileId) : [];
	const baseOrder = explicitOrder ?? (explicitProfiles.length > 0 ? explicitProfiles : listProfilesForProvider(store, providerKey));
	if (baseOrder.length === 0) return [];
	const isValidProfile = (profileId) => {
		const cred = store.profiles[profileId];
		if (!cred) return false;
		if (normalizeProviderId(cred.provider) !== providerKey) return false;
		const profileConfig = cfg?.auth?.profiles?.[profileId];
		if (profileConfig) {
			if (normalizeProviderId(profileConfig.provider) !== providerKey) return false;
			if (profileConfig.mode !== cred.type) {
				if (!(profileConfig.mode === "oauth" && cred.type === "token")) return false;
			}
		}
		if (cred.type === "api_key") return Boolean(cred.key?.trim());
		if (cred.type === "token") {
			if (!cred.token?.trim()) return false;
			if (typeof cred.expires === "number" && Number.isFinite(cred.expires) && cred.expires > 0 && now >= cred.expires) return false;
			return true;
		}
		if (cred.type === "oauth") return Boolean(cred.access?.trim() || cred.refresh?.trim());
		return false;
	};
	let filtered = baseOrder.filter(isValidProfile);
	const allBaseProfilesMissing = baseOrder.every((profileId) => !store.profiles[profileId]);
	if (filtered.length === 0 && explicitProfiles.length > 0 && allBaseProfilesMissing) filtered = listProfilesForProvider(store, providerKey).filter(isValidProfile);
	const deduped = dedupeProfileIds(filtered);
	if (explicitOrder && explicitOrder.length > 0) {
		const available = [];
		const inCooldown = [];
		for (const profileId of deduped) {
			const cooldownUntil = resolveProfileUnusableUntil(store.usageStats?.[profileId] ?? {}) ?? 0;
			if (typeof cooldownUntil === "number" && Number.isFinite(cooldownUntil) && cooldownUntil > 0 && now < cooldownUntil) inCooldown.push({
				profileId,
				cooldownUntil
			});
			else available.push(profileId);
		}
		const cooldownSorted = inCooldown.toSorted((a, b) => a.cooldownUntil - b.cooldownUntil).map((entry) => entry.profileId);
		const ordered = [...available, ...cooldownSorted];
		if (preferredProfile && ordered.includes(preferredProfile)) return [preferredProfile, ...ordered.filter((e) => e !== preferredProfile)];
		return ordered;
	}
	const sorted = orderProfilesByMode(deduped, store);
	if (preferredProfile && sorted.includes(preferredProfile)) return [preferredProfile, ...sorted.filter((e) => e !== preferredProfile)];
	return sorted;
}
function orderProfilesByMode(order, store) {
	const now = Date.now();
	const available = [];
	const inCooldown = [];
	for (const profileId of order) if (isProfileInCooldown(store, profileId)) inCooldown.push(profileId);
	else available.push(profileId);
	const sorted = available.map((profileId) => {
		const type = store.profiles[profileId]?.type;
		return {
			profileId,
			typeScore: type === "oauth" ? 0 : type === "token" ? 1 : type === "api_key" ? 2 : 3,
			lastUsed: store.usageStats?.[profileId]?.lastUsed ?? 0
		};
	}).toSorted((a, b) => {
		if (a.typeScore !== b.typeScore) return a.typeScore - b.typeScore;
		return a.lastUsed - b.lastUsed;
	}).map((entry) => entry.profileId);
	const cooldownSorted = inCooldown.map((profileId) => ({
		profileId,
		cooldownUntil: resolveProfileUnusableUntil(store.usageStats?.[profileId] ?? {}) ?? now
	})).toSorted((a, b) => a.cooldownUntil - b.cooldownUntil).map((entry) => entry.profileId);
	return [...sorted, ...cooldownSorted];
}

//#endregion
//#region src/agents/auth-profiles.ts
var auth_profiles_exports = /* @__PURE__ */ __exportAll({ ensureAuthProfileStore: () => ensureAuthProfileStore });

//#endregion
export { resolveAuthStorePath as C, CODEX_CLI_PROFILE_ID as D, CLAUDE_CLI_PROFILE_ID as E, updateAuthProfileStoreWithLock as S, resolveAuthProfileDisplayLabel as T, setAuthProfileOrder as _, markAuthProfileFailure as a, ensureAuthProfileStore as b, resolveApiKeyForProfile as c, generateChutesPkce as d, parseOAuthCallbackInput as f, markAuthProfileGood as g, listProfilesForProvider as h, isProfileInCooldown as i, CHUTES_AUTHORIZE_ENDPOINT as l, dedupeProfileIds as m, resolveAuthProfileOrder as n, markAuthProfileUsed as o, repairOAuthProfileIdMismatch as p, getSoonestCooldownExpiry as r, resolveProfileUnusableUntilForDisplay as s, auth_profiles_exports as t, exchangeChutesCodeForTokens as u, upsertAuthProfile as v, resolveAuthStorePathForDisplay as w, loadAuthProfileStore as x, upsertAuthProfileWithLock as y };