from __future__ import annotations import logging import os from .types import MSTeamsAuthType logger = logging.getLogger(__name__) class MSTeamsConfigAdapter: def __init__(self): ... def list_account_ids(self, config: dict) -> list[str]: accounts = config.get("channels", {}).get("msteams", {}).get("accounts", {}) if accounts: return list(accounts.keys()) return ["default"] def _resolve_channel_config(self, config: dict) -> dict: return config.get("channels", {}).get("msteams", {}) or {} async def resolve_account(self, account_id: str) -> dict: raw = self._load_raw(account_id) app_id = raw.get("appId") or os.environ.get("MSTEAMS_APP_ID", "") app_password = raw.get("appPassword") or os.environ.get("MSTEAMS_APP_PASSWORD", "") tenant_id = raw.get("tenantId") or os.environ.get("MSTEAMS_TENANT_ID", "") auth_type = MSTeamsAuthType.SECRET certificate_path = raw.get("certificatePath") use_managed_identity = raw.get("useManagedIdentity") if certificate_path or use_managed_identity: auth_type = MSTeamsAuthType.FEDERATED return { "account_id": account_id, "app_id": app_id, "app_password": app_password, "tenant_id": tenant_id, "auth_type": auth_type, "config": raw, } def _load_raw(self, account_id: str) -> dict: try: from yuxi.channel.config.snapshot import get_latest_snapshot snapshot = get_latest_snapshot() if snapshot and hasattr(snapshot, "config"): channel_cfg = snapshot.config.get("channels", {}).get("msteams", {}) or {} accounts = channel_cfg.get("accounts", {}) or {} if account_id in accounts: return accounts[account_id] if "default" in accounts: return accounts["default"] return channel_cfg except Exception: pass return {} def is_configured(self, account: dict) -> bool: return bool(account.get("app_id") and account.get("app_password")) def is_enabled(self, account: dict, config: dict) -> bool: channel_cfg = self._resolve_channel_config(config) return channel_cfg.get("enabled", True) def disabled_reason(self, account: dict, config: dict) -> str: if not self.is_configured(account): return "App ID 或 App Password 未配置" return "" def describe_account(self, account: dict, config: dict) -> dict: return { "account_id": account.get("account_id", "default"), "app_id": account.get("app_id", ""), "tenant_id": account.get("tenant_id", ""), "configured": self.is_configured(account), } def default_account_id(self, config: dict) -> str: accounts = self._resolve_channel_config(config).get("accounts", {}) if accounts: return next(iter(accounts.keys())) return "default" def resolve_allow_from(self, config: dict, account_id: str | None = None) -> list[str | int] | None: channel_cfg = self._resolve_channel_config(config) allow_from = channel_cfg.get("allowFrom", []) return allow_from if allow_from else None def has_configured_state(self, config: dict) -> bool: channel_cfg = self._resolve_channel_config(config) return bool(channel_cfg.get("appId") or channel_cfg.get("accounts"))