Engine
Node.js
The Substrate only appends history. Nothing inside Cardinal gets edited out.
Ticks
Micro tick
Scintilla movement and physics. Resource consumption and regeneration. Environmental state update. Collision and proximity detection.
Cognitive tick
Need state evaluation. Action selection via policy. Continuity read/write. Social evaluation. Communication signal emission and reception.
Chronicle tick
Event aggregation and tagging. Continuity decay application. History compression. Cultural marker evaluation. Groq narration. SQLite flush.
95% pure heuristic JS. Groq only for chronicle narration, Continuity distillation, and communication utterances, through groq/client.js only.Implementation
Node.js
SQLite / better-sqlite3
Groq
Float32Array
Railway
Express + HTML/CSS/JS (Railway)
cardinal/ ├── world/ # grid, seasons, entities ├── scintillae/ # state, perception, policy ├── continuity/ # layers, decay, knowledge ├── communication/ # signals, language ├── substrate/ # micro, cognitive, chronicle ticks ├── db/ # schema, flush ├── observer/ # immutable event log ├── groq/ # all Groq calls ├── config.js └── index.js
Event system
Chronicle tick reads the event stream and builds compressed narrative: not “scintilla 0042 gathered berries at tick 18273” but “group near the river valley has sustained itself on river resources for 14 simulated years.”
Logging
{
"tick": 18273,
"scintilla": "scintilla_0042",
"action": "gather",
"resource": "berries",
"location": [22, 91],
"need_state": {
"hunger": 0.61,
"thirst": 0.43,
"fatigue": 0.28,
"fear": 0.12
},
"trigger": "hunger_threshold_crossed"
}An action without its trigger is just noise. Invisible to Scintillae. Readable by the Administrator.