"""Dashboard route - main landing page""" import platform import shutil import socket import time from datetime import datetime from pathlib import Path from flask import Blueprint, render_template, current_app, jsonify from markupsafe import Markup from web.auth import login_required dashboard_bp = Blueprint('dashboard', __name__) def get_system_info(): info = { 'hostname': socket.gethostname(), 'platform': platform.platform(), 'python': platform.python_version(), 'arch': platform.machine(), } try: info['ip'] = socket.gethostbyname(socket.gethostname()) except Exception: info['ip'] = '127.0.0.1' # Uptime try: with open('/proc/uptime') as f: uptime_secs = float(f.read().split()[0]) days = int(uptime_secs // 86400) hours = int((uptime_secs % 86400) // 3600) info['uptime'] = f"{days}d {hours}h" except Exception: info['uptime'] = 'N/A' return info def get_tool_status(): from core.paths import find_tool tools = {} for tool in ['nmap', 'tshark', 'upnpc', 'msfrpcd', 'wg']: tools[tool] = find_tool(tool) is not None return tools def get_module_counts(): from core.menu import MainMenu menu = MainMenu() menu.load_modules() counts = {} for name, info in menu.modules.items(): cat = info.category counts[cat] = counts.get(cat, 0) + 1 counts['total'] = len(menu.modules) return counts @dashboard_bp.route('/') @login_required def index(): config = current_app.autarch_config system = get_system_info() tools = get_tool_status() modules = get_module_counts() # LLM status llm_backend = config.get('autarch', 'llm_backend', fallback='local') if llm_backend == 'transformers': llm_model = config.get('transformers', 'model_path', fallback='') elif llm_backend == 'claude': llm_model = config.get('claude', 'model', fallback='') elif llm_backend == 'huggingface': llm_model = config.get('huggingface', 'model', fallback='') else: llm_model = config.get('llama', 'model_path', fallback='') # UPnP status upnp_enabled = config.get_bool('upnp', 'enabled', fallback=False) return render_template('dashboard.html', system=system, tools=tools, modules=modules, llm_backend=llm_backend, llm_model=llm_model, upnp_enabled=upnp_enabled, ) @dashboard_bp.route('/manual') @login_required def manual(): """Render the user manual as HTML.""" manual_path = Path(__file__).parent.parent.parent / 'user_manual.md' content = manual_path.read_text(encoding='utf-8') if manual_path.exists() else '# Manual not found' try: import markdown html = markdown.markdown(content, extensions=['tables', 'fenced_code', 'toc']) except ImportError: html = '
' + content.replace('<', '<') + ''
return render_template('manual.html', manual_html=Markup(html))
@dashboard_bp.route('/manual/windows')
@login_required
def manual_windows():
"""Render the Windows-specific user manual."""
manual_path = Path(__file__).parent.parent.parent / 'windows_manual.md'
content = manual_path.read_text(encoding='utf-8') if manual_path.exists() else '# Windows manual not found'
try:
import markdown
html = markdown.markdown(content, extensions=['tables', 'fenced_code', 'toc'])
except ImportError:
html = '' + content.replace('<', '<') + ''
return render_template('manual.html', manual_html=Markup(html))
@dashboard_bp.route('/api/modules/reload', methods=['POST'])
@login_required
def reload_modules():
"""Re-scan modules directory and return updated counts + module list."""
from core.menu import MainMenu
menu = MainMenu()
menu.load_modules()
counts = {}
modules = []
for name, info in menu.modules.items():
cat = info.category
counts[cat] = counts.get(cat, 0) + 1
modules.append({
'name': name,
'category': cat,
'description': info.description,
'version': info.version,
})
counts['total'] = len(menu.modules)
return jsonify({'counts': counts, 'modules': modules, 'total': counts['total']})