Cognets

A cognet is a cognition engine: the program that runs a mind.

A game engine runs a game. It holds the game's world, runs its logic many times a second, and draws the result. A cognet does the same for something that senses, believes and acts — a chat agent, a thermostat, a robot mapping a room.

a cognet
senses→cognetworldsystems→actionsfrom the bodyruns 60 times a secondto the body

The body is whatever the mind is attached to: a chat window, a simulator, a robot. It sends what it senses and does what it is told. The cognet never touches it directly — which is why the same mind runs in all three.

Why it exists

Most minds start as one loop: read the sensors, call a model, decide, act. That works until the mind grows. Perception, memory, maps and planning all run at different speeds, all depend on each other, and the loop becomes a tangle nobody can trace.

Games hit the same wall decades ago, and solved it with an entity component system. A cognet brings that design to minds:

  • Everything the mind believes lives in one world, as plain data.
  • Every piece of logic is a small system that says what it reads and what it writes.
  • The engine runs the systems on a clock, in the right order, and records everything.

You write the parts. The engine handles the loop, the order, the threads and the record.

How it works

The engine runs in ticks — on a clock, say 60 times a second, or only when something arrives for a chat agent that sleeps between messages. Every tick:

  1. Senses arrive. Whatever the body felt since the last tick lands in the world.
  2. Systems run. Each reads what it declared and writes what it declared. The engine orders them from those declarations: a system that reads temperature runs after the one that writes it. Nobody writes that order down.
  3. Actions leave. Whatever the systems told the body to do.

Systems never call each other. They only meet in the world.

What you write

Components are what the mind can believe. Plain types, in any of the three languages:

// types/room/room.components.ts
export interface Temperature {
    celsius: f64
    sensed: f64
}

export interface Heating {
    on: boolean
}

Systems read some components and write others:

// src/room/warmth.system.ts
const TARGET = 21

export default defineSystem({
    reads: ["temperature"],
    writes: ["heating"],

    run() {
        for (const room of ecs.query({ components: ["temperature"] })) {
            ecs.set({ id: room.id, components: { heating: { on: room.temperature.celsius < TARGET } } })
        }
    },
})

Put three of these together and you have a thermostat. The engine wires them by what they read and write:

the thermostat
senses→feel→temperature→warmth→heating→heat→actions

Pick a language per system, not per project. A cognet can be all TypeScript, all Python, or whatever each part is best written in — the world doesn't know the difference.

What you get for free

Because every system declares what it reads and writes, the engine knows the whole mind's structure before it runs a single tick. That buys:

OrderSystems run in the order their data implies. No main function, no call graph.
One owner per beliefTwo systems writing heating is refused before the first tick, by name.
ParallelismSystems that share nothing run on other cores, untouched.
A full recordEvery value read and written, by whom, on which tick.

That record is what the debugger reads. Ask who writes a belief, and who depends on it:

$ axonl debug graph --component heating
{"ok":true,"data":{"name":"room/heating","writtenBy":["room/warmth"],"readBy":["room/heat"], …}}

Where to go next