diff options
| author | Agando <roduccomm@gmail.com> | 2026-05-27 06:00:43 +0200 |
|---|---|---|
| committer | Agando <roduccomm@gmail.com> | 2026-05-27 06:00:43 +0200 |
| commit | 212708b464c2bdbdd9670c00804623dca0729d2c (patch) | |
| tree | ee190cbb0d1524350baea641df65aa19817744b5 /modules/core/module-system.js | |
| parent | f4d934d341056142da1212c845eeeb170fd452c2 (diff) | |
auto: 2026-05-27_06:00 changes
Diffstat (limited to 'modules/core/module-system.js')
| -rw-r--r-- | modules/core/module-system.js | 95 |
1 files changed, 93 insertions, 2 deletions
diff --git a/modules/core/module-system.js b/modules/core/module-system.js index f21946a..b561ef2 100644 --- a/modules/core/module-system.js +++ b/modules/core/module-system.js @@ -14,6 +14,9 @@ 'factory-reset': 'factory-reset [--confirm] — Wipe all webx11_ data (VFS, config, AI profile, mindmaps, themes, all localStorage)', 'reset-vfs': 'reset-vfs [--confirm] — Clear only the virtual filesystem (keeps settings, modules, AI profile)', 'logs': 'logs [n] [LEVEL] — Show last n log entries (optionally filtered by level: INFO/WARN/ERROR)', + 'logrotate': 'logrotate — Rotate current.log to a dated archive (auto-cleans old)', + 'health-check': 'health-check — Audit VFS size, modules, logs, trash, skills, tool failures', + 'memory-map-export': 'memory-map-export — Generate memory map markdown from memory/index.json', 'font-size': 'font-size <8-32> — Set terminal font size (persists across sessions)', 'setfont': 'setfont <8-32> — Alias for font-size', 'smart-prompt': 'smart-prompt [on|off] — Toggle context-aware prompt (shows name, skills, sessions, memory, edits)', @@ -92,6 +95,93 @@ this.terminal.print('--- Logs (last ' + tail.length + ') ---', 'info'); tail.forEach(l => this.terminal.print(l, l.includes('[ERROR]') ? 'error' : 'info')); }; + // Auto-rotate logs on startup (silently) + this._autoRotateLogs(); + this.commands['logrotate'] = () => { + const rotated = this._autoRotateLogs(true); + if (rotated) { + this.terminal.print('Log rotated: ' + rotated, 'success'); + } else { + this.terminal.print('Log rotation not needed (<50KB, <500 lines)', 'info'); + } + }; + this.commands['health-check'] = () => this._healthCheck(); + this.commands['memory-map-export'] = () => this._memoryMapExport(); + } + _autoRotateLogs(force = false) { + try { + const content = this.terminal.fs.readFile('/logs/current.log') || ''; + const lines = content.split('\n').filter(l => l); + const size = content.length; + if (!force && size < 51200 && lines.length < 500) return null; + const now = new Date(); + const stamp = now.getFullYear() + '-' + + String(now.getMonth()+1).padStart(2,'0') + '-' + + String(now.getDate()).padStart(2,'0') + '_' + + String(now.getHours()).padStart(2,'0') + '00'; + this.terminal.fs.writeFile('/logs/' + stamp + '.log', content); + this.terminal.fs.writeFile('/logs/current.log', ''); + // Clean oldest rotated logs (>10) + const logsDir = this.terminal.fs.readDir('/logs'); + if (logsDir && logsDir.content) { + const rotated = Object.keys(logsDir.content) + .filter(k => k.endsWith('.log') && k !== 'current.log') + .sort(); + while (rotated.length > 10) { + const oldest = rotated.shift(); + this.terminal.fs.deleteFile('/logs/' + oldest); + } + } + return stamp + '.log'; + } catch (e) { return null; } + } + _healthCheck() { + const fs = this.terminal.fs; + let warnings = 0; + this.terminal.print('╔══════════════════════════════════════╗', 'info'); + this.terminal.print('║ 🔍 SYSTEM HEALTH CHECK ║', 'info'); + this.terminal.print('╚══════════════════════════════════════╝', 'info'); + // VFS size + const dump = JSON.stringify(fs.root).length; + const vfsOk = dump < 524288; + this.terminal.print(`VFS size: ${(dump/1024).toFixed(1)}KB ${vfsOk ? '✅' : '⚠️ > 512KB'}`, vfsOk ? 'info' : 'warning'); + if (!vfsOk) warnings++; + // Modules + const modTotal = Object.keys(this.terminal.moduleManager.modules || {}).length; + this.terminal.print(`Modules loaded: ${modTotal} ✅`, 'info'); + // Logs + const logContent = fs.readFile('/logs/current.log') || ''; + const logLines = logContent.split('\n').filter(l => l).length; + this.terminal.print(`Current log: ${logLines} lines`, logLines > 500 ? 'warning' : 'info'); + if (logLines > 500) warnings++; + // Trash + const trashList = fs.listTrash ? fs.listTrash() : []; + this.terminal.print(`Trash items: ${trashList.length}`, 'info'); + // Skills + const skillIdx = fs.fsReadJSON ? (fs.fsReadJSON('/skills/index.json') || {}) : {}; + const skillCount = Object.keys(skillIdx).length; + this.terminal.print(`Skills: ${skillCount}`, skillCount > 0 ? 'info' : 'warning'); + if (skillCount === 0) warnings++; + // Summary + this.terminal.print('─'.repeat(40), 'text-muted'); + if (warnings === 0) { + this.terminal.print('All checks passed ✅', 'success'); + } else { + this.terminal.print(`${warnings} warning(s) found`, 'warning'); + } + } + _memoryMapExport() { + const fs = this.terminal.fs; + const idx = fs.fsReadJSON ? (fs.fsReadJSON('/memory/index.json') || {}) : null; + if (!idx) { + this.terminal.print('No memory index found at /memory/index.json', 'error'); + return; + } + this.terminal.print('---\nname: adaptive-memory-map\ndescription: Auto-generated from memory/index.json\ntags: [memory, context, tracking, adaptation]\ncategory: system\n---\n', 'info'); + for (const [k,v] of Object.entries(idx)) { + this.terminal.print(`## ${k}\n- Tasks: ${v.tasks || 0}\n- Updated: ${v.updated || 'unknown'}\n- Summary: ${(v.summary || '').substring(0,100)}...`, 'info'); + } + this.terminal.print('(Not saved — render to file with memory-map-export > /memory/reference.md if desired)', 'text-muted'); } handleHelp(args) { const helpMap = this.terminal.moduleManager.getAllHelp(); @@ -116,8 +206,9 @@ files: ['ls','ll','cat','put','rm','mv','cp','mkdir','rmdir','cd','pwd','find','grep','head','tail','sort','wc','touch','tree','du','upload','download','vfs-export','vfs-import','edit','diff'], ai: ['ai','ask','ai-clear','ai-system','ai-context','ai-allow','ai-deny','ai-stop','ai-model'], search: ['search','s','ddg','duck','fetch','web','extract'], - tools: ['calc','cron-every','cron-list','cron-stop','cron-clear','wpm','mindmap','theme','voice','alias','unalias'], - system: ['help','clear','cls','echo','mem','status','font-size','setfont','smart-prompt','logs','preview','factory-reset','reset-vfs'], + tools: ['calc','cron-every','cron-list','cron-stop','cron-clear','wpm','mindmap','theme','voice','alias','unalias', + 'which','env','date','cal','yes','seq','base64','printf','cut','uniq','hostname','whoami','basename','dirname','sleep','expand'], + system: ['help','clear','cls','echo','mem','status','font-size','setfont','smart-prompt','logs','preview','factory-reset','reset-vfs','export','unset','script','set','test'], net: ['server','servers','server-check','server-remove','monitor'], mods: ['modules','listmods','loadmod','removemod','load-local','loadlocal','startup-modules'], ollama: ['ollama','ollamaconnect','ollamadisconnect','ollamamodels','ollamasetmodel','ollamasetproxy','models','model-info','model-pull','model-delete','model-run'], |