#!/usr/bin/env python3
"""
Neurotron — entrypoint oficial.
Arranque do dashboard + thread cognitiva.
Totalmente silencioso fora do LogBus.
"""

import sys
import threading
import time
import traceback
from pathlib import Path

from neurotron.logbus import logbus
from neurotron.cortex import Cortex


# =============================================================================
# DASHBOARD (modo texto minimalista)
# =============================================================================

def dashboard_loop(ctx: Cortex):
    """
    Dashboard com scroll “real”.
    Mantém:
      - Linha 1: estado
      - Linha 2: separador
      - Linhas 3..102: janela de 100 linhas do logbus
    """
    start = time.time()

    MAX_LINES = 40              # janela visível
    LOG_START_ROW = 3            # linha onde os logs começam

    # limpar ecrã e esconder cursor
    sys.stdout.write("\033[2J\033[H\033[?25l")
    sys.stdout.flush()

    try:
        while True:
            uptime = int(time.time() - start)
            h = uptime // 3600
            m = (uptime % 3600) // 60
            s = uptime % 60

            mode = (ctx.mode or "").upper()
            tick = ctx.tick

            if mode == "PERSISTENT":
                mode_str = "\033[1;34mPERSISTENT\033[0m"
            elif mode == "DIAGNOSTIC":
                mode_str = "\033[1;33mDIAGNOSTIC\033[0m"
            else:
                mode_str = mode

            header = (
                f"UP: {h:02}:{m:02}:{s:02}  "
                f"TICK: {tick:0.2f}s  "
                f"MODO: {mode_str}"
            )

            # Header
            sys.stdout.write("\033[1;1H" + header + "\033[K")
            sys.stdout.write("\033[2;1H" + "─" * 80 + "\033[K")

            # ----------------------------------------------
            # SCROLL WINDOW (esta é a magia ✨)
            # ----------------------------------------------
            logs = logbus.tail(MAX_LINES)
            row = LOG_START_ROW

            for line in logs:
                truncated = line[:256]
                sys.stdout.write(f"\033[{row};1H{truncated}\033[K")
                row += 1

            # Limpar linhas abaixo caso sobrem
            # sys.stdout.write(f"\033[{row};1H\033[J")
            # sys.stdout.flush()

            time.sleep(0.1)

    finally:
        sys.stdout.write("\033[?25h")
        sys.stdout.flush()

# =============================================================================
# CICLO COGNITIVO
# =============================================================================

def cognitive_loop(ctx: Cortex):
    """Loop cognitivo principal (observe → think → act → rest)."""
    try:
        ctx.boot()
        logbus.info("Ciclo cognitivo iniciado (observe → think → act → rest)")

        while True:
            ctx.observe()   # sensores, discos, vitals
            ctx.think()     # neurónios decidem
            ctx.act()       # motor executa
            ctx.rest()      # heartbeat + diag + sleep

    except Exception as e:
        logbus.error(f"Fatal no ciclo cognitivo: {repr(e)}")

        tb = traceback.format_exc()
        for line in tb.splitlines():
            logbus.error(line)

        ctx.shutdown("fatal exception")
        raise

# =============================================================================
# MAIN
# =============================================================================

def main():
    """
    Entrada principal do Neurotron.
    Inicia:
      - cortex
      - dashboard (thread)
      - ciclo cognitivo (thread)
    """

    runtime_dir = "/opt/kernel/neurotron/runtime"
    log_dir     = "/opt/kernel/neurotron/logs"

    Path(runtime_dir).mkdir(parents=True, exist_ok=True)
    Path(log_dir).mkdir(parents=True, exist_ok=True)

    ctx = Cortex(runtime_dir=runtime_dir, log_dir=log_dir)

    # threads
    t_dash = threading.Thread(target=dashboard_loop, args=(ctx,), daemon=True)
    t_cog  = threading.Thread(target=cognitive_loop, args=(ctx,), daemon=True)

    t_dash.start()
    t_cog.start()

    # thread principal fica apenas a dormir
    try:
        while True:
            time.sleep(1)
    except KeyboardInterrupt:
        logbus.warn("Interrompido pelo utilizador")
        ctx.shutdown("CTRL+C")


if __name__ == "__main__":
    main()

