import sys
import os
import threading

try:
    sys.stdout.reconfigure(encoding="utf-8")
    sys.stderr.reconfigure(encoding="utf-8")
except Exception:
    pass

# Ensure the project root is on sys.path so `app.*` imports resolve correctly
PROJECT_DIR = os.path.dirname(os.path.abspath(__file__))
if PROJECT_DIR not in sys.path:
    sys.path.insert(0, PROJECT_DIR)


def run_admin_panel():
    """Run the Flask admin panel in a daemon thread."""
    try:
        from app.admin.app import create_admin_app
        from app.core.config import get_setting

        port = int(get_setting("system.admin_port", "5000"))
        app = create_admin_app()
        print(f"[ADMIN] Panel starting on  http://0.0.0.0:{port}")
        app.run(host="0.0.0.0", port=port, use_reloader=False, debug=False, threaded=True)
    except Exception as exc:
        print(f"[ADMIN ERROR] {exc}")


def main():
    # ── 1. Initialise database (create tables) ────────────────────────────────
    from app.core.database import init_db
    init_db()

    # ── 2. Seed default data on first run ─────────────────────────────────────
    from init_app import seed_all
    seed_all()

    # ── 3. Set up logging (including DB handler) ──────────────────────────────
    from app.core.logger import get_logger, add_db_handler
    add_db_handler()
    logger = get_logger()
    logger.info("[RUN] FinanceGPT service starting...")

    # This is the single-process deployment: the admin panel runs in this same
    # process as the engines, so it's safe to act on them directly.
    from app.core.state import mark_engine_process
    mark_engine_process()

    # ── Start the async audit worker + record a startup audit event ───────────
    from app.core import audit
    from app.models import audit_log as al
    audit.start_worker()
    audit.record(module=al.MODULE_SYSTEM, action="startup", severity=al.SEV_INFO,
                 message="سرویس FinanceGPT راه‌اندازی شد")

    # ── Resume account-based forward tasks left active/paused before a restart
    #    (their engine control state lives in memory only) ─────────────────────
    try:
        from app.forwarding.service import ForwardTaskService
        resumed = ForwardTaskService().resume_active()
        if resumed:
            logger.info(f"[RUN] Resumed {resumed} forward task(s) from previous run")
    except Exception as exc:
        logger.error(f"[RUN] Failed to resume forward tasks: {exc}")

    # ── Re-arm forward-approval bot pollers so تایید/رد buttons on any
    #    already-sent approval message keep working after a restart (poller
    #    state is in-memory only) ────────────────────────────────────────────
    try:
        from app.services.forward_bot_service import resume_pollers
        fb_resumed = resume_pollers()
        if fb_resumed:
            logger.info(f"[RUN] Started {fb_resumed} forward-approval bot poller(s)")
    except Exception as exc:
        logger.error(f"[RUN] Failed to start forward-approval bot pollers: {exc}")

    # ── Resume fixed messages left active/paused before a restart (same gap
    #    as forward tasks — engine control state lives in memory only) ────────
    try:
        from app.fixed_messages.service import FixedMessageService
        fm_resumed = FixedMessageService().resume_active()
        if fm_resumed:
            logger.info(f"[RUN] Resumed {fm_resumed} fixed message(s) from previous run")
    except Exception as exc:
        logger.error(f"[RUN] Failed to resume fixed messages: {exc}")

    # ── 4. Start admin panel in background thread ─────────────────────────────
    admin_thread = threading.Thread(target=run_admin_panel, daemon=True)
    admin_thread.start()

    # ── 5. Build and run the Telegram client (asyncio loop, main thread) ──────
    #       Mirrors the original `with tg: tg.loop.run_until_complete(main())`
    #       pattern so Telethon manages its own event loop correctly.
    from app.services.telegram_service import create_client, run_telegram_service
    from app.core.state import set_telegram_client

    tg_client = create_client()
    set_telegram_client(tg_client)
    logger.info("[RUN] Telegram client created. Connecting...")

    with tg_client:
        tg_client.loop.run_until_complete(run_telegram_service(tg_client))


if __name__ == "__main__":
    main()
