#!/usr/bin/env python3
"""Echo Task Board API — thin HTTP router.

All endpoint logic lives in `dashboard/handlers/*.py`. This file is
responsible only for URL dispatch, CORS, JSON response helpers, and
server bootstrap.
"""
import json
import sys
from http.server import HTTPServer, SimpleHTTPRequestHandler
from pathlib import Path

# Make dashboard/ importable for the handler submodules (constants,
# habits_helpers, handlers.*). Tests rely on this as well.
_DASH = Path(__file__).parent
if str(_DASH) not in sys.path:
    sys.path.insert(0, str(_DASH))

from constants import (  # noqa: E402  re-exported for tests
    ALLOWED_WORKSPACES,
    BASE_DIR,
    ECHO_CORE_DIR,
    ECHO_LOG_FILE,
    ECHO_SESSIONS_FILE,
    ECO_SERVICES,
    GIT_WORKSPACE,
    GITEA_ORG,
    GITEA_TOKEN,
    GITEA_URL,
    HABITS_FILE,
    KANBAN_DIR,
    NOTES_DIR,
    TOOLS_DIR,
    VENV_PYTHON,
    WORKSPACE_DIR,
)
from handlers.cron import CronHandlers  # noqa: E402
from handlers.eco import EcoHandlers  # noqa: E402
from handlers.files import FilesHandlers  # noqa: E402
from handlers.git import GitHandlers  # noqa: E402
from handlers.habits import HabitsHandlers  # noqa: E402
from handlers.pdf import PDFHandlers  # noqa: E402
from handlers.workspace import WorkspaceHandlers  # noqa: E402
from handlers.youtube import YoutubeHandlers  # noqa: E402

# Shared navigation injected into every served .html via <!--NAV--> marker.
NAV_HTML = '''<header class="header">
    <a href="/echo/index.html" class="logo">
        <i data-lucide="circle-dot"></i>
        Echo
    </a>
    <nav class="nav">
        <a href="/echo/index.html" class="nav-item" data-page="index">
            <i data-lucide="layout-dashboard"></i>
            <span>Dashboard</span>
        </a>
        <a href="/echo/workspace.html" class="nav-item" data-page="workspace">
            <i data-lucide="code"></i>
            <span>Workspace</span>
        </a>
        <a href="/echo/notes.html" class="nav-item" data-page="notes">
            <i data-lucide="file-text"></i>
            <span>KB</span>
        </a>
        <a href="/echo/habits.html" class="nav-item" data-page="habits">
            <i data-lucide="dumbbell"></i>
            <span>Habits</span>
        </a>
        <a href="/echo/files.html" class="nav-item" data-page="files">
            <i data-lucide="folder"></i>
            <span>Files</span>
        </a>
        <button class="theme-toggle" onclick="toggleTheme()" title="Schimbă tema">
            <i data-lucide="sun" id="themeIcon"></i>
        </button>
    </nav>
</header>
<script>
(function(){
    var path = window.location.pathname;
    var m = path.match(/([^\\/]+?)(?:\\.html)?$/);
    var page = m ? m[1] : 'index';
    if (!page || page === 'echo') page = 'index';
    var item = document.querySelector('.nav-item[data-page="' + page + '"]');
    if (item) item.classList.add('active');
})();
</script>'''


class TaskBoardHandler(
    GitHandlers,
    HabitsHandlers,
    EcoHandlers,
    FilesHandlers,
    PDFHandlers,
    YoutubeHandlers,
    WorkspaceHandlers,
    CronHandlers,
    SimpleHTTPRequestHandler,
):
    """HTTP request handler — dispatches to handler-mixin methods."""

    # ── shared utilities ────────────────────────────────────────
    def _read_post_json(self):
        """Read a JSON body from the POST request."""
        content_length = int(self.headers['Content-Length'])
        post_data = self.rfile.read(content_length).decode('utf-8')
        return json.loads(post_data)

    def send_json(self, data, code=200):
        self.send_response(code)
        self.send_header('Content-Type', 'application/json')
        self.send_header('Access-Control-Allow-Origin', '*')
        self.send_header('Cache-Control', 'no-cache, no-store, must-revalidate')
        self.send_header('Pragma', 'no-cache')
        self.send_header('Expires', '0')
        self.end_headers()
        self.wfile.write(json.dumps(data).encode())

    def do_OPTIONS(self):
        self.send_response(200)
        self.send_header('Access-Control-Allow-Origin', '*')
        self.send_header('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS')
        self.send_header('Access-Control-Allow-Headers', 'Content-Type')
        self.end_headers()

    # ── dispatch ────────────────────────────────────────────────
    def do_GET(self):
        from datetime import datetime as _dt
        if self.path == '/api/status':
            self.send_json({'status': 'ok', 'time': _dt.now().isoformat()})
        elif self.path == '/api/git' or self.path.startswith('/api/git?'):
            self.handle_git_status()
        elif self.path == '/api/cron' or self.path.startswith('/api/cron?'):
            self.handle_cron_status()
        elif self.path == '/api/habits':
            self.handle_habits_get()
        elif self.path.startswith('/api/files'):
            self.handle_files_get()
        elif self.path.startswith('/api/diff'):
            self.handle_git_diff()
        elif self.path == '/api/workspace' or self.path.startswith('/api/workspace?'):
            self.handle_workspace_list()
        elif self.path.startswith('/api/workspace/git/diff'):
            self.handle_workspace_git_diff()
        elif self.path.startswith('/api/workspace/logs'):
            self.handle_workspace_logs()
        elif self.path == '/api/eco/status' or self.path.startswith('/api/eco/status?'):
            self.handle_eco_status()
        elif self.path == '/api/eco/sessions' or self.path.startswith('/api/eco/sessions?'):
            self.handle_eco_sessions()
        elif self.path.startswith('/api/eco/sessions/content'):
            self.handle_eco_session_content()
        elif self.path.startswith('/api/eco/logs'):
            self.handle_eco_logs()
        elif self.path == '/api/eco/doctor':
            self.handle_eco_doctor()
        elif self.path.startswith('/api/'):
            self.send_error(404)
        else:
            # Inject shared nav into served HTML pages via <!--NAV--> marker.
            rel = self.path.lstrip('/').split('?')[0]
            if rel.endswith('.html'):
                try:
                    fpath = (KANBAN_DIR / rel).resolve()
                    fpath.relative_to(KANBAN_DIR.resolve())
                except (ValueError, OSError):
                    self.send_error(403)
                    return
                if fpath.is_file():
                    html = fpath.read_text('utf-8').replace('<!--NAV-->', NAV_HTML)
                    body = html.encode('utf-8')
                    self.send_response(200)
                    self.send_header('Content-Type', 'text/html; charset=utf-8')
                    self.send_header('Content-Length', str(len(body)))
                    self.send_header('Cache-Control', 'no-cache')
                    self.end_headers()
                    self.wfile.write(body)
                    return
            super().do_GET()

    def do_POST(self):
        if self.path == '/api/youtube':
            self.handle_youtube()
        elif self.path == '/api/files':
            self.handle_files_post()
        elif self.path == '/api/refresh-index':
            self.handle_refresh_index()
        elif self.path == '/api/pdf':
            self.handle_pdf_post()
        elif self.path == '/api/habits':
            self.handle_habits_post()
        elif self.path.startswith('/api/habits/') and self.path.endswith('/check'):
            self.handle_habits_check()
        elif self.path.startswith('/api/habits/') and self.path.endswith('/skip'):
            self.handle_habits_skip()
        elif self.path == '/api/workspace/run':
            self.handle_workspace_run()
        elif self.path == '/api/workspace/stop':
            self.handle_workspace_stop()
        elif self.path == '/api/workspace/git/commit':
            self.handle_workspace_git_commit()
        elif self.path == '/api/workspace/git/push':
            self.handle_workspace_git_push()
        elif self.path == '/api/workspace/delete':
            self.handle_workspace_delete()
        elif self.path == '/api/eco/restart':
            self.handle_eco_restart()
        elif self.path == '/api/eco/stop':
            self.handle_eco_stop()
        elif self.path == '/api/eco/sessions/clear':
            self.handle_eco_sessions_clear()
        elif self.path == '/api/eco/git-commit':
            self.handle_eco_git_commit()
        elif self.path == '/api/eco/restart-taskboard':
            self.handle_eco_restart_taskboard()
        else:
            self.send_error(404)

    def do_PUT(self):
        if self.path.startswith('/api/habits/'):
            self.handle_habits_put()
        else:
            self.send_error(404)

    def do_DELETE(self):
        if self.path.startswith('/api/habits/') and '/check' in self.path:
            self.handle_habits_uncheck()
        elif self.path.startswith('/api/habits/'):
            self.handle_habits_delete()
        else:
            self.send_error(404)


if __name__ == '__main__':
    import os
    port = 8088
    os.chdir(KANBAN_DIR)

    print(f"Starting Echo Task Board API on port {port}")
    httpd = HTTPServer(('0.0.0.0', port), TaskBoardHandler)
    httpd.serve_forever()
