Relocate the ~6k-file docs tree from the repo root into plugins/document-navigator/docs/ so the plugin is self-contained and portable. docs/superpowers/ (specs and plans) stays at the repo root. Moved via cp+rm rather than git mv because directory rename() fails with EPERM on this WSL /mnt DrvFs mount; git rename-detection pairs the identical-content files at commit time. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
6.0 KiB
6.0 KiB
@suaveplan/ecs - Archetype-based Entity Component System with Uint32 bitset queries, phase-ordered system scheduler, entity-ID recycling, Zod-validated component schemas, structured errors, and OpenTelemetry instrumentation
Archetype-based Entity Component System with Uint32-backed bitset queries, phase-ordered system scheduling, entity-ID recycling, Zod-validated component schemas, structured errors, and OpenTelemetry instrumentation. Universal — runs identically in Bun, Node, and the browser.
Documentation tree
- archetype — An
Archetyperepresents the unique combination of component types shared by a group of entities. All entities with th…- archetype — An
Archetyperepresents the unique combination of component types shared by a group of entities. All entities with th…
- archetype — An
- bitset —
BitSetis the foundational mask primitive used by archetypes, queries, and the component registry inside `@suaveplan/…- bitset —
BitSetis the foundational mask primitive used by archetypes, queries, and the component registry inside `@suaveplan/…
- bitset —
- component-registry —
ComponentRegistrytranslatesComponentSchemareferences into stable integer IDs. These IDs are used as bit position…- component-registry —
ComponentRegistrytranslatesComponentSchemareferences into stable integer IDs. These IDs are used as bit position…
- component-registry —
- entity-pool —
EntityPoolis the entity-ID allocator. It hands out positive integer IDs onallocate(), recycles freed IDs on `free…- entity-pool —
EntityPoolis the entity-ID allocator. It hands out positive integer IDs onallocate(), recycles freed IDs on `free…
- entity-pool —
- errors —
EcsErroris the typed error class for every failure mode raised by@suaveplan/ecs. It extendsSuaveplanErrorfrom…- ecs-error —
EcsErroris the typed error class for every failure mode raised by@suaveplan/ecs. It extendsSuaveplanErrorfrom…
- ecs-error —
- observability — This module owns the OpenTelemetry instruments used by
@suaveplan/ecs. There are two metrics — `ecs.entity.lifecycle_…- otel — This module owns the OpenTelemetry instruments used by
@suaveplan/ecs. There are two metrics — `ecs.entity.lifecycle_…
- otel — This module owns the OpenTelemetry instruments used by
- query —
Querycompiles a declarativeQueryDescriptor(include/ optionalexcludeschemas) into bitset masks and evaluat…- query —
Querycompiles a declarativeQueryDescriptor(include/ optionalexcludeschemas) into bitset masks and evaluat…
- query —
- schema —
defineComponentis the canonical factory forComponentSchemaobjects. It produces a deep-frozen descriptor pairing…- schema —
defineComponentis the canonical factory forComponentSchemaobjects. It produces a deep-frozen descriptor pairing…
- schema —
- system — A system is the unit of behaviour in an ECS — a function that runs over every entity matching a query and mutates com…
- system — A system is the unit of behaviour in an ECS — a function that runs over every entity matching a query and mutates com…
- world —
Worldis the central container for an ECS instance. It owns the component registry, entity pool, archetype graph, que…- world —
Worldis the central container for an ECS instance. It owns the component registry, entity pool, archetype graph, que…
- world —
Install
bun add @suaveplan/ecs
Quick start
import { createWorld, defineComponent, defineSystem } from "@suaveplan/ecs";
const Position = defineComponent("Position", { x: 0, y: 0 });
const Velocity = defineComponent("Velocity", { dx: 1, dy: 0 });
const world = createWorld();
world.addSystem(defineSystem({
name: "physics",
query: { include: [Position, Velocity] },
execute: ({ entities, world, dt }) => {
for (const entity of entities) {
const p = world.getComponent(entity, Position)!;
const v = world.getComponent(entity, Velocity)!;
world.setComponent(entity, Position, {
x: p.x + v.dx * dt,
y: p.y + v.dy * dt,
});
}
},
}));
const player = world.spawn();
world.addComponent(player, Position);
world.addComponent(player, Velocity);
world.execute(1 / 60);
Modules
bitset/—Uint32Array-backed bitset primitive.component-registry/— stable-ID registry for component schemas.entity-pool/— entity-ID allocator with recycling and generations.archetype/— column-oriented storage with O(1) swap-remove.query/— bitset-driven query compiler.system/— phase-priority system scheduler.schema/—defineComponentfactory with optional Zod validator.world/— central container; spawn/despawn, components, queries, systems, snapshot/restore.errors/—EcsErrorand theECS_CODESregistry.observability/— OTel counters and histograms.types/— every public type alias and interface.
Quality gates
bunx turbo lint typecheck test --filter=@suaveplan/ecs
bunx turbo test:coverage --filter=@suaveplan/ecs # 100% statement+branch+function+line
bun run docs:check --filter=@suaveplan/ecs
License
MIT © Suaveplan Team