integration
Integration guide
How to run AQL programmatically and how it maps to HTTP endpoints.
Calling the engine
Import runAql from the playground module (same package as the UI):
import { runAql } from "./_lib/aql-engine";
import type { AqlExecutionState } from "./_lib/aql-types";
const state: AqlExecutionState = {
serverUrl: "https://your-host",
mainNodeId: "<main-node-id>",
sid: null, // or existing session id from POST /api/agent-play/session
nodePasswordMaterial: "<hex from nodeCredentialsMaterialFromHumanPassphrase>",
spaceCatalogId: null,
spaceNodeId: null,
spacePasswordMaterial: null,
targetAmenityKind: null,
targetAgentId: null,
targetNodeId: null,
timeoutMs: 8000,
headers: {},
};
const result = await runAql({
source: yourAqlSourceString,
state,
});
// result.response — last SHOW / FETCH / SEND / INSPECT payload
// result.headers — last HTTP response headers from the runtime client
// result.nextState — updated sid, targets, headers, timeout
// result.diagnostics — parse, semantic, or runtime errors
The playground prepends LET serverUrl = "..."; embedders should do the same or avoid $serverUrl in scripts.
Execution state
| Field | Role |
|---|---|
serverUrl |
Base URL for fetch (/api/...) |
mainNodeId |
Main node id for intercom + inspect |
sid |
Agent Play session id (?_sid= on RPC); set by CONNECT or externally |
nodePasswordMaterial |
Hex string used as x-node-passw for node APIs |
spaceCatalogId |
Catalog space id after USE SPACE NODE |
spaceNodeId |
Space node id used for x-node-id on space-scoped RPCs |
spacePasswordMaterial |
Hex passphrase material for the space node |
targetAmenityKind |
"shop" | "supermarket" | "car_wash" after USE AMENITY |
targetAgentId |
Resolved agent player id after USE AGENT NODE |
targetNodeId |
Selected agent node id |
timeoutMs |
Used where the executor honors timeout |
headers |
Extra headers merged into outbound requests (via WITH HEADER) |
Runtime client (PlaygroundRuntimeClient)
aql-runtime-client.ts implements:
| Method | HTTP |
|---|---|
ensureSession |
POST /api/agent-play/session |
fetchSnapshot |
POST /api/agent-play/sdk/rpc?sid=… — op: "getWorldSnapshot" |
fetchSessionDetails |
GET /api/agent-play/session/details?sid=…&includeSnapshot=1&eventsLimit=50 |
inspectMainNode |
GET /api/nodes with x-node-id, x-node-passw |
sendIntercomCommand |
POST /api/agent-play/sdk/rpc?sid=… — op: "intercomCommand" (chat) |
Responses are JSON objects augmented with __http.status and __http.headers for diagnostics.
Root key and validation
The playground validates the main node before Connect using NEXT_PUBLIC_AGENT_PLAY_ROOT_KEY. Server-side node creation and validation follow Node ID v1.
Extending AQL
- Lexer — Add keywords to
KEYWORDSinaql-lexer.tsif new reserved words are needed. - Parser — New statement kinds in
aql-parser.ts; extendAqlStatement. - Validator — Rules in
aql-validator.ts. - Executor — Behavior + HTTP mapping in
aql-executor.ts; add RPC helpers to the runtime client. - Tests —
aql-engine.test.ts,aql-autocomplete.test.ts.
Keep language-reference.md and Examples updated when grammar changes.
SDK parity
For production automation (CI, servers), prefer RemotePlayWorld from @agent-play/sdk — connect, getWorldSnapshot, intercom APIs — rather than reimplementing AQL. Use AQL when you want a scriptable operator UI aligned with the playground.