Pular para o conteúdo principal

Architecture Overview

AI Supreme Council is a zero-hosting bot management platform that runs entirely in the browser. The production output is a single index.html file (~980 KB) assembled from 80 modular source files. There are no external runtime dependencies -- only JavaScript and WASM ship to the browser.

Single-File Architecture

The app is a single self-contained HTML file. During development, it is split into src/ parts for smaller context windows and focused editing. The build.sh script concatenates all 80 parts back into index.html in a strict order.

src/shell-head.html        \
src/shell-style.html |
src/shell-body.html |
src/core-boot.js |
src/core-auth-main.js | build.sh
... | ---------> index.html (~980 KB)
src/settings-main.js |
src/miniprograms.js |
src/pwa.js |
src/shell-bottom.js /
aviso

Never edit index.html directly. Always edit the corresponding file in src/, then run ./build.sh to reassemble.

Global Namespace

All modules register on the window.AIS global namespace. The namespace is initialized in src/core-boot.js:

window.AIS = { version: '2.0.0', type: 'aiscouncil' };
AIS.PLATFORM_VERSION = '1.0.0';
AIS.ABI_VERSION = 1;

Cross-module communication uses a lightweight event bus:

AIS.on('event', handler);   // subscribe
AIS.off('event', handler); // unsubscribe
AIS.emit('event', data); // publish

Module System: AIS.lazy()

Modules use a Qwik-style lazy hydration pattern. The factory function is deferred until the module is first accessed via a property getter on AIS:

if (!AIS.Council) AIS.lazy('Council', function() {
'use strict';
// module code here
return { run, renderCouncilMessage, estimateCost };
});

On first access (e.g., AIS.Council.run()), the getter fires, executes the factory, replaces itself with the returned module object, and returns it. Subsequent accesses hit the plain value with no overhead.

WASM kernel modules can still override a JS module by setting AIS.Council = wasmModule before the first access, because the property is defined as configurable: true.

Module Categories

Core Modules (always loaded)

Core modules are defined inside a single <script> block (core-boot.js through core-end.js). They execute eagerly at page load and form the foundation of the app.

ModuleFilePurpose
AIS.Authcore-auth-main.js, core-auth-local.js, core-auth-init.jsWebAuthn/Passkey + OAuth login, session management, auth cookie
AIS.Billingcore-billing.jsSubscription tier, trial, managed plan
AIS.Codeccore-codec.jsBase80 encoding, VLQ versioning, deflate compression
AIS.Storagecore-storage.jsIndexedDB + optional SQLite WASM, offline-first
AIS.Providerscore-providers.js, core-providers-builtin.jsLLM provider registry, SSE streaming factory
AIS.UIcore-ui.jsDOM utilities, markdown renderer, toast notifications
AIS.Sessioncore-session.jsBot session CRUD (IndexedDB-backed)
AIS.Chatcore-chat.jsChat history, streaming message send/receive
AIS.Configcore-config.jsBot config panel bindings, URL sync
AIS.Appcore-app-botlist.js, core-app-switch.js, core-app-events.js, core-app-search.js, core-app-init.jsApplication controller, init, routing, bot management

WASM-Replaceable Modules (lazy-loaded)

Each WASM-replaceable module lives in its own <script> block and uses the AIS.lazy() pattern. They only execute when first accessed.

ModuleFilePurpose
AIS.Registryregistry.jsCommunity model registry, 24h cache, GitHub fallback
AIS.Gridgrid.jsModel table/card renderer (compiled from TypeScript)
AIS.Councilcouncil.jsMulti-model deliberation engine (7 styles)
AIS.Wizardwizard.jsDual-mode first-run setup wizard
AIS.Visionvision.jsImage input for vision models (paste/upload)
AIS.Memorymemory.jsPersistent per-bot key-value memory
AIS.ImageGenimagegen.jsImage generation (DALL-E, Grok Imagine, OpenRouter)
AIS.Toolstools.jsTool/function calling format normalization
AIS.Remindersreminders.jsScheduled messages via /remind command
AIS.Themesthemes.jsVisual theme system
AIS.Templatestemplates-registry.jsSystem prompt templates, welcome screens
AIS.ModelPickermodel-picker.jsSortable model browser

Infrastructure Modules (lazy-loaded)

ModuleFilePurpose
AIS.ModuleLoadermoduleloader.jsHot-swap module lifecycle, OPFS cache
AIS.Pluginsplugins.jsPlugin system: manifest validation, hooks
AIS.MCPmcp.jsModel Context Protocol (tools + resources)
AIS.Channelschannels-core.js, channels-whatsapp.js, channels-adapters.js, channels-stubs.jsChannel adapters (Telegram, Discord, Matrix, Slack, WhatsApp)
AIS.Sandboxsandbox.jsWASM tool sandbox (Pyodide, QuickJS, SQLite)
AIS.Publishpublish.jsSEO + static HTML publishing
AIS.Perfperf.jsPerformance monitoring
AIS.P2Pp2p.jsP2P collaboration via WebRTC + CRDTs

Platform Modules

ModuleFilePurpose
AIS.Settingssettings-main.jsGlobal settings dialog (all sections)
AIS.I18ni18n.jsInternationalization
AIS.MiniProgramsminiprograms.jsMini-program runtime (sandboxed iframes)
AIS.Docsdocs.jsInline docs viewer
AIS.Profilesprofiles.jsMulti-model profile/council templates
AIS.Croncron.jsBrowser-based scheduler

CSS Architecture

The app uses a classless CSS approach. Styles target semantic HTML elements and IDs instead of classes.

Selector TypeExampleUse Case
ID#header, #sidebar-left, #config-bodyUnique layout containers
Semantic element#messages > article, article menu buttonMessages, actions, navigation
Data attribute[data-from="user"], [data-variant="primary"]Variants (message role, button type)
State class.active, .collapsed, .mobile-openJS-toggled states
Component class.council-member-row, .status-dotDynamic JS-created components
Utility class.f1, .sc, .dimOne-off inline style replacement

Semantic HTML elements used: <header>, <main>, <aside>, <section>, <footer>, <nav>, <article>, <menu>, <details>, <dialog>, <output>.

informação

Classes are only used for three cases: state toggles (.active, .collapsed), dynamic JS components (.council-member-row), and utility shorthands (.f1, .sc). If you can target an element with a semantic selector or data attribute, do that instead of adding a class.

Storage Architecture

Storage is split between synchronous and asynchronous stores:

StorageKeysReason
localStorage (sync)ais-theme, ais-apikey-*, ais-user, ais-ollama-endpointSync reads needed at boot time
IndexedDB (async, unlimited)ais-bots, ais-chat-*, ais-addon-manifestsLarge data, no 5 MB limit
SQLite WASM (optional, OPFS)Binary blobsLazy-loaded for concurrent access

On first boot, AIS.Storage.init() auto-migrates data from localStorage to IndexedDB.

Provider Architecture

Providers are registered via AIS.Providers.register(). Most providers use the shared openaiCompatible() SSE streaming factory, which handles:

  • Server-Sent Events parsing
  • Token-by-token streaming callbacks
  • AbortController signal support
  • Token counting from response headers

Six built-in providers are registered in core-providers-builtin.js:

ProviderAPI StyleAuthNotes
AnthropicNative (Messages API)x-api-key headerCustom streaming format
OpenAIOpenAI-compatibleBearer tokenStandard SSE
xAIOpenAI-compatibleBearer tokenGrok models
Google GeminiNative (Gemini API)?key= query paramAvoids CORS preflight
OpenRouterOpenAI-compatibleBearer token300+ models, free tier
OllamaOpenAI-compatibleNoneLocal LLMs, auto-detects models

All API keys are stored locally (localStorage['ais-apikey-{provider}']). Keys are sent directly from the browser to the provider -- never proxied through any server.

Design Principles

The codebase follows strict design principles that every change must satisfy:

  1. HTML5 native first -- Use <dialog>, <output>, hidden attribute, CSS animations before JS equivalents.
  2. Zero polling -- No requestAnimationFrame loops, no setInterval, no setTimeout for animation. Event-driven only.
  3. Passive listeners -- All non-cancelable events use { passive: true }.
  4. Event delegation -- Single listener on container, not per-item listeners on dynamic lists.
  5. 14px minimum font -- All text must be readable by vision LLMs. No text below 14px.
  6. VLM-friendly layout -- 48px+ click targets, large toggles, high contrast. Settings and menus display all primary items without scrolling on 1920x1080.
  7. Reduced motion -- @media (prefers-reduced-motion: reduce) disables all animations.
  8. CSS containment -- contain: strict on sidebars, content-visibility: auto on scrollable lists.
dica

Before adding any feature, ask the four decision-gate questions:

  1. Can the browser do this natively?
  2. Does this require a server? (If yes, make it optional.)
  3. Does this scale to 1 million bots per device?
  4. What are the memory and CPU costs?

WASM Kernel

The optional WASM kernel (kernel/) is written in Zig and compiles to ~5.5 KB. It provides low-level primitives for the module system: slot management, hook dispatch, ring buffer I/O, and write-ahead logging.

The kernel operates on a 64 MB SharedArrayBuffer with defined memory regions for module segments, ring buffers, WAL, and scratch arena. JS modules can be replaced by WASM equivalents at runtime without breaking the lazy-loading contract.

API Architecture

The platform uses split Workers for different concerns:

WorkerDomainPurpose
aiscouncil-apiapi.aiscouncil.comBilling, usage, key vending, geo
aiscouncil-authauth.aiscouncil.comOAuth callbacks, token verification

API base URLs are set at boot from domain detection and can be overridden via localStorage['ais-api-base'] for local development.