Docssdk 0.0.0Aether homeOpen Aether

Automation

Run named system scripts in QuickJS and let the server validate every emitted effect.

1 minute read

System automation is the trusted game-action path for code that rolls, reads documents, keeps state, or proposes document changes. The source string runs in a QuickJS sandbox, never through import() inside the server process.

#Declare a script

systems/my-system/src/index.tsTypeScript
const scripts = [{
  id: "apply-damage",
  name: "Roll and apply damage",
  source: `
    const target = aether.getDoc(aether.args.docId);
    if (!target) throw new Error("Target not found");
    const damage = aether.roll("2d6+2");
    const next = Math.max(0, target.system.hp.value - damage.total);
    aether.mutate(target.id, [
      { op: "set", path: ["system", "hp", "value"], value: next }
    ]);
    aether.log("Applied " + damage.total + " damage");
  `,
}];

Return the scripts in setup, then invoke one from a native-view gesture.runAutomation action or another host surface.

#Available authority

The automation host supplies bounded APIs for documents, dice, namespaced state, mutations, and logs. A script does not receive file, process, network, or application module access. State is kept in a GM-owned document namespaced to the author so two packages do not collide.

The server checks the caller's world policy before starting the script. Each emitted patch then passes ordinary permission, revision, capability, and schema validation. A script cannot turn a valid invocation into an unchecked database write.

#Verify

systems/demo-system/src/index.ts contains damage and stateful counter scripts. packages/automation/test/sandbox.test.ts exercises the actual sandbox. Run:

TerminalShell
bun test packages/automation/test/sandbox.test.ts
bun run --filter @aether/demo-system typecheck

Automation is contributed by the active system today. Mods can request automation.run to invoke those named scripts as the current member; they do not supply in-process server code.

Was this page helpful?