#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
使用系统 Chrome 浏览器版本的登录函数
"""

import asyncio
import tempfile
import logging

logger = logging.getLogger(__name__)

class CRMLoginError(Exception):
    """CRM 登录错误"""
    pass


async def login_to_crm_with_system_browser(url: str, username: str, password: str,
                                          headless: bool = False,
                                          use_chrome: bool = True,
                                          use_edge: bool = False) -> dict:
    """
    使用系统安装的 Chrome 或 Edge 浏览器登录 CRM

    Args:
        url: CRM URL
        username: 用户名
        password: 密码
        headless: 是否无头模式（系统浏览器不支持无头模式，会忽略）
        use_chrome: 使用 Chrome
        use_edge: 使用 Edge

    Returns:
        dict: 包含 ReqClientId 和 orgId 的字典
    """
    try:
        from playwright.async_api import async_playwright
    except ImportError:
        raise CRMLoginError("Playwright 未安装")

    async with async_playwright() as p:
        browser = None
        context = None

        try:
            # 选择浏览器类型
            if use_chrome:
                browser_type = p.chromium
                channel = "chrome"  # 使用系统 Chrome
                logger.info("使用系统 Chrome 浏览器")
            elif use_edge:
                browser_type = p.chromium
                channel = "msedge"  # 使用系统 Edge
                logger.info("使用系统 Edge 浏览器")
            else:
                # 使用 Playwright 下载的 Chromium
                browser_type = p.chromium
                channel = None
                logger.info("使用 Playwright Chromium")

            logger.info(f"启动浏览器 (channel={channel}, headless={headless})...")

            # 启动浏览器
            launch_options = {
                "headless": headless,
                "channel": channel
            }

            # 如果使用系统浏览器，忽略 headless
            if channel and headless:
                logger.warning("系统浏览器不支持无头模式，将使用可见模式")
                launch_options["headless"] = False

            browser = await browser_type.launch(**launch_options)

            context_options = {
                "viewport": {"width": 1280, "height": 720},
                "user_agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36"
            }

            context = await browser.new_context(**context_options)
            page = await context.new_page()

            login_url = f"{url.rstrip('/')}/MDP/"
            logger.info(f"访问: {login_url}")
            await page.goto(login_url, timeout=30000, wait_until='domcontentloaded')

            await asyncio.sleep(2)

            current_url = page.url
            if 'main.aspx' not in current_url:
                # 填写登录表单
                username_selectors = [
                    'input[name="username"]',
                    'input[type="text"]',
                    'input[id*="user"]',
                    'input[placeholder*="user" i]',
                ]

                username_field = None
                for selector in username_selectors:
                    try:
                        username_field = await page.wait_for_selector(selector, timeout=2000)
                        if username_field:
                            logger.info(f"找到用户名输入框: {selector}")
                            break
                    except:
                        continue

                if not username_field:
                    raise CRMLoginError("找不到用户名输入框")

                await username_field.fill(username)
                logger.info(f"用户名: {username}")

                password_selectors = [
                    'input[name="password"]',
                    'input[type="password"]',
                    'input[id*="pass"]',
                ]

                password_field = None
                for selector in password_selectors:
                    try:
                        password_field = await page.wait_for_selector(selector, timeout=2000)
                        if password_field:
                            logger.info(f"找到密码输入框: {selector}")
                            break
                    except:
                        continue

                if not password_field:
                    raise CRMLoginError("找不到密码输入框")

                await password_field.fill(password)
                logger.info("密码已输入")

                submit_selectors = [
                    'button[type="submit"]',
                    'input[type="submit"]',
                    'button:has-text("Log")',
                    'button:has-text("Sign")',
                ]

                submit_button = None
                for selector in submit_selectors:
                    try:
                        submit_button = await page.wait_for_selector(selector, timeout=2000)
                        if submit_button:
                            logger.info(f"找到提交按钮: {selector}")
                            break
                    except:
                        continue

                if submit_button:
                    await submit_button.click()
                else:
                    await password_field.press('Enter')

            logger.info("等待登录完成...")
            try:
                await page.wait_for_url("**/main.aspx**", timeout=30000)
            except:
                pass

            await asyncio.sleep(2)

            cookies = await context.cookies()
            logger.info(f"获取到 {len(cookies)} 个 cookies")

            req_client_id = None
            org_id = None

            for cookie in cookies:
                if cookie['name'] == 'ReqClientId':
                    req_client_id = cookie['value']
                elif cookie['name'] == 'orgId':
                    org_id = cookie['value']

            if not req_client_id or not org_id:
                raise CRMLoginError("无法提取 ReqClientId 或 orgId")

            logger.info("CRM 登录成功")

            return {
                'ReqClientId': req_client_id,
                'orgId': org_id
            }

        except CRMLoginError:
            raise
        except Exception as e:
            raise CRMLoginError(f"登录错误: {e}")
        finally:
            if context:
                await context.close()
            if browser:
                await browser.close()


# 测试代码
if __name__ == "__main__":
    async def test():
        import json
        import sys

        logging.basicConfig(level=logging.INFO)

        # 加载配置
        try:
            with open("config.json", "r", encoding="utf-8") as f:
                config = json.load(f)
        except:
            print("错误: 无法加载配置文件")
            sys.exit(1)

        # 导入密码管理器
        import mdp_termination
        password = mdp_termination.PasswordManager.decrypt_password(config.get('password_file', 'password.enc'))

        print("测试使用系统浏览器登录...")
        print(f"URL: {config['crm_url']}")
        print(f"用户名: {config['crm_username']}")
        print(f"使用 Chrome: 是")
        print()

        try:
            cookies = await login_to_crm_with_system_browser(
                config['crm_url'],
                config['crm_username'],
                password,
                headless=False,
                use_chrome=True
            )

            print("\n✅ 登录成功!")
            print(f"ReqClientId: {cookies['ReqClientId'][:20]}...")
            print(f"orgId: {cookies['orgId'][:20]}...")

        except Exception as e:
            print(f"\n❌ 登录失败: {e}")
            import traceback
            traceback.print_exc()

    asyncio.run(test())
