DSL schema reference
A ruleset is a JSON document that describes a business process as a tree of steps. Every field documented below is derived from the Zod schema the engine actually enforces at save time — this page is generated from that schema, so it cannot describe a shape the engine would reject, nor omit one it accepts.
Schema version 1 is the only version this engine supports. No step executes in this phase: the schema fixes the document shape and its validation, not any run behaviour.
Envelope fields
The top-level fields of a ruleset document:
| Field | Presence |
|---|---|
schemaVersion | required |
name | required |
envelope | optional |
subjectKey | optional |
timezone | optional |
inputSchema | required |
output | required |
outputSchema | required |
documentInputs | optional |
datasets | optional |
steps | required |
timezone is optional and defaults to UTC when the ruleset declares none;
when declared, it must be a zone identifier the host platform's own timezone
database recognizes, and the same value is what every date/time function in
the ruleset resolves against.
Step types
Every step declares a type drawn from this fixed, six-member catalog:
| Step type |
|---|
compute |
branch |
foreach |
lookup |
xmlTransform |
extract |
check |
Amendments to schema version 1
Schema version 1 is amended in place while no tenant ruleset exists; every amendment is dated and recorded here so "version 1" does not silently denote two different document shapes across repository history. This is a declaration of what changed and when — it does not prove that an earlier document had the shape a given row now describes.
| Date | Field | Summary |
|---|---|---|
| 2026-10-09 | xmlTransform.sourceOutput | Added an optional named source view with exact parsed simple text, string attributes and ordered child arrays alongside unchanged XML conversion. |
| 2026-10-08 | steps[].type: check | Added a check step with a boolean violation condition, rule code, editable severity and localized message; its value is null or a violation object. |
| 2026-10-08 | steps[].rule.message | Added localized messages with optional German and English members, requiring at least one non-empty language. |
| 2026-08-28 | inputSchema | Added as a REQUIRED field — every ruleset must declare the JSON Schema of the input it expects, with no unconstrained fallback for a document that omits it. |
| 2026-08-28 | branch.output | Added as a REQUIRED field — names a step present as a direct child of every case and of the fallback list when present; the branch step's own type becomes the union of what each of those named steps infers to. |
| 2026-08-28 | foreach.output | Added as a REQUIRED field — names a step present as a direct child of the foreach body; the foreach step's own type becomes an array of that named step's type, collected once per iteration. |
| 2026-08-28 | assertedOutput | Added as an OPTIONAL field on every step type — declares the shape of a step's output in the same dialect as the declared input schema, for a position where the checker cannot otherwise work the shape out; legal only where the checker agrees it is needed. |
| 2026-09-07 | output | Added as a REQUIRED field — names a step present at the top level of the ruleset; that step's value becomes the run's declared output. |
| 2026-09-07 | outputSchema | Added as a REQUIRED field — declares the shape of the value the output step produces, in the same dialect as the declared input schema, so a run can never report a result as schema-conformant without a schema actually having been checked. |
| 2026-09-07 | scale | Added as an OPTIONAL keyword on a number or integer node in the declared output schema — constrains the number of decimal places a value may carry, checked as an integer comparison; an integer node carries a scale of zero without restating it. |
| 2026-09-07 | xmlTransform.conversion | Narrowed to the ratified rl-xml-json-v1 profile: 'namespaces' is now a declared map from namespace URI to the prefix the ruleset wants that namespace's elements and attributes to emit under, rather than a three-member choice; 'repeatedElements' and 'mixedContent' each admit exactly one member. A namespace prefix map may be empty; an undeclared namespace encountered in a document is refused when the step actually runs, naming the namespace, rather than at save time. A future, explicitly versioned profile may relax the mixed-content refusal without breaking a ruleset saved under this one. |
| 2026-09-11 | documentInputs | Added as an OPTIONAL top-level field, independent of inputSchema — declares the document roles a ruleset accepts. Each role names an integer minItems/maxItems cardinality between 0 and 20 and a non-empty list of accepted media types drawn from a fixed platform set; a role name is an ASCII identifier and may not be 'input', 'steps' or 'documents'. |
| 2026-09-29 | datasets | Added as an OPTIONAL top-level field, independent of inputSchema — declares the reference datasets a ruleset reads, at most 20 per ruleset. Each entry names its row schema in the same dialect as the declared input schema (nesting allowed, object at the top), a key of one to four fields, and optional indexes. Key and index fields must point to single values; a key field must be required, never empty, and text or a whole number. At most 6 text, 6 number and 2 yes/no fields may be key or indexed fields together. A dataset name is an ASCII identifier of up to 64 characters starting with a letter. |
| 2026-09-29 | lookup.orderBy | Added as an OPTIONAL field on a lookup step — orders the matching rows by one to three fields, each ascending or descending; the dataset's key is the implicit final tie-break, so the order is always total. Empty values sort last when ascending and first when descending. |
| 2026-09-29 | lookup.match.flags | Added as an OPTIONAL field on a lookup step's match criterion — a list of normalizations applied to both sides of that comparison, drawn from 'trim' and 'caseInsensitive' with no member repeated. Legal on text fields only. |
| 2026-09-30 | required | Narrowed on every object node of every declared schema (input, output, asserted output and dataset row schemas): each entry in 'required' must be a string naming one of the same object's own declared properties. A document that named an undeclared property was previously accepted with that entry silently ignored, and a non-string entry was silently dropped; both are now refused, naming the position of the entry. |
| 2026-10-02 | envelope.pages | Added as an OPTIONAL field of 'envelope' — the total number of document pages one run may send to extraction, a positive whole number. Like the other envelope fields it may not exceed the platform ceiling, and an omitted value inherits that ceiling. |
| 2026-10-02 | extract.reading | Added as an OPTIONAL field of an extract step — how the pages of the document are read before a model sees them: 'auto' (the platform chooses page by page), 'textLayer' (only the text the file already carries) or 'ocr' (every page read as an image). An omitted value means 'auto'. |
| 2026-10-02 | ai.retries | Added as an OPTIONAL field of an extract step's 'ai' block — how many corrective follow-up requests the model may receive after an answer that does not match the target schema, a whole number from 0 to 2. An omitted value means one follow-up. |
| 2026-10-02 | ai.plausibility | Added as an OPTIONAL field of an extract step's 'ai' block — a list of one to 16 plausibility checks over the extracted value, each with a name and a condition. A name starts with a letter, holds only letters, digits and underscores, is at most 64 characters long, and may be used by only one check of the step. |
| 2026-10-02 | ai.cache | Changed from a REQUIRED to an OPTIONAL field of an extract step's 'ai' block. An omitted value means results are reused (mode 'reuse'); a document that still declares the field is valid unchanged. |
| 2026-10-02 | inputSchema.description | Added as an OPTIONAL note on any node of a declared schema (input, output, asserted output, dataset row and extract target schemas) — a string describing what the field holds. It is an annotation only: it changes no type, and a value that is not a string is refused. |
| 2026-10-02 | inputSchema.format | Added as an OPTIONAL keyword on a text node of a declared schema (input, output, asserted output, dataset row and extract target schemas): a type of 'string', or a type array naming 'string' and otherwise only 'null' — either 'date' or 'date-time'. It is an annotation only: the field stays text and its type does not change. Any other value, or the keyword on a node that is not text, is refused. |
| 2026-10-02 | documentInputs.mediaTypes | Widened: the media types a document role may accept now also include 'image/png', 'image/jpeg', 'image/tiff', 'text/html' and 'message/rfc822'. A document that declared only the earlier types is valid unchanged. |
| 2026-10-02 | lookup.match | Narrowed: a lookup step's 'match' list may hold at most 64 criteria, where it was previously bounded only by the size of the document. A step with more than 64 criteria is refused when the ruleset is saved. |
| 2026-10-02 | ai.targetSchema | Narrowed: an extract step's target schema ('ai.targetSchema') was any JSON object; it is now read in the same closed dialect as the declared schemas, refusing unknown keywords, open objects, names ending in the reserved confidence suffix and schemas over the strict-output limits; a decimal field may declare scale. |
JSON Schema
The full JSON Schema, generated from rulesetSchema via Zod v4's native
z.toJSONSchema():
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"type": "object",
"properties": {
"schemaVersion": {
"type": "number"
},
"name": {
"type": "string",
"minLength": 1
},
"envelope": {
"type": "object",
"properties": {
"wallClockMs": {
"type": "integer",
"minimum": 1,
"maximum": 9007199254740991
},
"stepCount": {
"type": "integer",
"minimum": 1,
"maximum": 9007199254740991
},
"memoryBytes": {
"type": "integer",
"minimum": 1,
"maximum": 9007199254740991
},
"foreachIterations": {
"type": "integer",
"minimum": 1,
"maximum": 9007199254740991
},
"modelCalls": {
"type": "integer",
"minimum": 1,
"maximum": 9007199254740991
},
"pages": {
"type": "integer",
"minimum": 1,
"maximum": 9007199254740991
}
},
"additionalProperties": false
},
"subjectKey": {
"type": "string"
},
"timezone": {
"type": "string"
},
"inputSchema": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {}
},
"output": {
"type": "string",
"minLength": 1
},
"outputSchema": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {}
},
"documentInputs": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"type": "object",
"properties": {
"minItems": {
"type": "integer",
"minimum": 0,
"maximum": 20
},
"maxItems": {
"type": "integer",
"minimum": 0,
"maximum": 20
},
"mediaTypes": {
"type": "array",
"items": {
"type": "string"
}
}
},
"required": [
"minItems",
"maxItems",
"mediaTypes"
],
"additionalProperties": false
}
},
"datasets": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"type": "object",
"properties": {
"schema": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {}
},
"key": {
"minItems": 1,
"maxItems": 4,
"type": "array",
"items": {
"type": "string",
"minLength": 1
}
},
"indexes": {
"type": "array",
"items": {
"type": "string",
"minLength": 1
}
}
},
"required": [
"schema",
"key"
],
"additionalProperties": false
}
},
"steps": {
"$ref": "#/$defs/__schema0"
}
},
"required": [
"schemaVersion",
"name",
"inputSchema",
"output",
"outputSchema",
"steps"
],
"additionalProperties": false,
"$defs": {
"__schema0": {
"type": "array",
"items": {
"oneOf": [
{
"type": "object",
"properties": {
"id": {
"type": "string"
},
"description": {
"type": "string"
},
"onError": {
"default": {
"mode": "hard"
},
"oneOf": [
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "hard"
}
},
"required": [
"mode"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "soft"
},
"fallback": {}
},
"required": [
"mode",
"fallback"
],
"additionalProperties": false
}
]
},
"assertedOutput": {},
"type": {
"type": "string",
"const": "check"
},
"violationWhen": {
"type": "string"
},
"rule": {
"type": "object",
"properties": {
"code": {
"type": "string",
"minLength": 2,
"maxLength": 64,
"pattern": "^[A-Z][A-Z0-9]*(-[A-Z0-9]+)*$"
},
"severity": {
"type": "string",
"enum": [
"error",
"warning"
]
},
"message": {
"type": "object",
"properties": {
"de": {
"type": "string"
},
"en": {
"type": "string"
}
},
"additionalProperties": false
}
},
"required": [
"code",
"severity",
"message"
],
"additionalProperties": false
}
},
"required": [
"id",
"onError",
"type",
"violationWhen",
"rule"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"id": {
"type": "string"
},
"description": {
"type": "string"
},
"onError": {
"default": {
"mode": "hard"
},
"oneOf": [
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "hard"
}
},
"required": [
"mode"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "soft"
},
"fallback": {}
},
"required": [
"mode",
"fallback"
],
"additionalProperties": false
}
]
},
"assertedOutput": {},
"type": {
"type": "string",
"const": "compute"
},
"outputs": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"type": "string"
}
}
},
"required": [
"id",
"onError",
"type",
"outputs"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"id": {
"type": "string"
},
"description": {
"type": "string"
},
"onError": {
"default": {
"mode": "hard"
},
"oneOf": [
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "hard"
}
},
"required": [
"mode"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "soft"
},
"fallback": {}
},
"required": [
"mode",
"fallback"
],
"additionalProperties": false
}
]
},
"assertedOutput": {},
"type": {
"type": "string",
"const": "branch"
},
"cases": {
"type": "array",
"items": {
"type": "object",
"properties": {
"when": {
"type": "string"
},
"steps": {
"$ref": "#/$defs/__schema0"
}
},
"required": [
"when",
"steps"
],
"additionalProperties": false
}
},
"otherwise": {
"$ref": "#/$defs/__schema0"
},
"output": {
"type": "string"
}
},
"required": [
"id",
"onError",
"type",
"cases",
"output"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"id": {
"type": "string"
},
"description": {
"type": "string"
},
"onError": {
"default": {
"mode": "hard"
},
"oneOf": [
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "hard"
}
},
"required": [
"mode"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "soft"
},
"fallback": {}
},
"required": [
"mode",
"fallback"
],
"additionalProperties": false
}
]
},
"assertedOutput": {},
"type": {
"type": "string",
"const": "foreach"
},
"collection": {
"type": "string"
},
"itemVar": {
"type": "string"
},
"indexVar": {
"type": "string"
},
"steps": {
"$ref": "#/$defs/__schema0"
},
"output": {
"type": "string"
}
},
"required": [
"id",
"onError",
"type",
"collection",
"itemVar",
"steps",
"output"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"id": {
"type": "string"
},
"description": {
"type": "string"
},
"onError": {
"default": {
"mode": "hard"
},
"oneOf": [
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "hard"
}
},
"required": [
"mode"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "soft"
},
"fallback": {}
},
"required": [
"mode",
"fallback"
],
"additionalProperties": false
}
]
},
"assertedOutput": {},
"type": {
"type": "string",
"const": "lookup"
},
"dataset": {
"type": "string"
},
"datasetVersion": {
"type": "string"
},
"match": {
"minItems": 1,
"maxItems": 64,
"type": "array",
"items": {
"type": "object",
"properties": {
"field": {
"type": "string"
},
"operator": {
"type": "string",
"enum": [
"equal",
"notEqual",
"lessThan",
"lessThanInclusive",
"greaterThan",
"greaterThanInclusive",
"in",
"notIn",
"contains",
"doesNotContain",
"approxEqual"
]
},
"value": {
"type": "string"
},
"tolerance": {
"type": "number"
},
"flags": {
"type": "array",
"items": {
"type": "string",
"enum": [
"trim",
"caseInsensitive"
]
}
}
},
"required": [
"field",
"operator",
"value"
],
"additionalProperties": false
}
},
"orderBy": {
"minItems": 1,
"maxItems": 3,
"type": "array",
"items": {
"type": "object",
"properties": {
"field": {
"type": "string",
"minLength": 1
},
"direction": {
"type": "string",
"enum": [
"asc",
"desc"
]
}
},
"required": [
"field",
"direction"
],
"additionalProperties": false
}
},
"cardinality": {
"type": "string",
"enum": [
"one",
"many"
]
},
"output": {
"type": "string"
}
},
"required": [
"id",
"onError",
"type",
"dataset",
"match",
"cardinality",
"output"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"id": {
"type": "string"
},
"description": {
"type": "string"
},
"onError": {
"default": {
"mode": "hard"
},
"oneOf": [
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "hard"
}
},
"required": [
"mode"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "soft"
},
"fallback": {}
},
"required": [
"mode",
"fallback"
],
"additionalProperties": false
}
]
},
"assertedOutput": {},
"type": {
"type": "string",
"const": "xmlTransform"
},
"input": {
"type": "string"
},
"xsd": {
"type": "object",
"properties": {
"ref": {
"type": "string"
},
"version": {
"type": "string"
}
},
"required": [
"ref",
"version"
],
"additionalProperties": false
},
"schematron": {
"type": "object",
"properties": {
"ref": {
"type": "string"
},
"version": {
"type": "string"
}
},
"required": [
"ref",
"version"
],
"additionalProperties": false
},
"conversion": {
"type": "object",
"properties": {
"convention": {
"type": "string",
"const": "rl-xml-json-v1"
},
"namespaces": {
"type": "object",
"propertyNames": {
"type": "string"
},
"additionalProperties": {
"type": "string"
}
},
"attributePrefix": {
"type": "string"
},
"repeatedElements": {
"type": "string",
"const": "always-array"
},
"mixedContent": {
"type": "string",
"const": "reject"
}
},
"required": [
"convention",
"namespaces",
"attributePrefix",
"repeatedElements",
"mixedContent"
],
"additionalProperties": false
},
"output": {
"type": "string"
},
"violationsOutput": {
"type": "string"
},
"sourceOutput": {
"type": "string",
"minLength": 1
}
},
"required": [
"id",
"onError",
"type",
"input",
"xsd",
"conversion",
"output",
"violationsOutput"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"id": {
"type": "string"
},
"description": {
"type": "string"
},
"onError": {
"default": {
"mode": "hard"
},
"oneOf": [
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "hard"
}
},
"required": [
"mode"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "soft"
},
"fallback": {}
},
"required": [
"mode",
"fallback"
],
"additionalProperties": false
}
]
},
"assertedOutput": {},
"type": {
"type": "string",
"const": "extract"
},
"document": {
"type": "string"
},
"reading": {
"type": "string",
"enum": [
"auto",
"textLayer",
"ocr"
]
},
"ai": {
"type": "object",
"properties": {
"model": {
"type": "string"
},
"prompt": {
"oneOf": [
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "generated"
}
},
"required": [
"mode"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"mode": {
"type": "string",
"const": "authored"
},
"text": {
"type": "string"
}
},
"required": [
"mode",
"text"
],
"additionalProperties": false
}
]
},
"targetSchema": {},
"cache": {
"type": "object",
"properties": {
"mode": {
"type": "string",
"enum": [
"reuse",
"bypass"
]
},
"ttlSeconds": {
"type": "integer",
"exclusiveMinimum": 0,
"maximum": 9007199254740991
}
},
"required": [
"mode"
],
"additionalProperties": false
},
"retries": {
"type": "integer",
"minimum": 0,
"maximum": 2
},
"plausibility": {
"minItems": 1,
"maxItems": 16,
"type": "array",
"items": {
"type": "object",
"properties": {
"name": {
"type": "string",
"pattern": "^[A-Za-z][A-Za-z0-9_]{0,63}$"
},
"condition": {
"type": "string"
}
},
"required": [
"name",
"condition"
],
"additionalProperties": false
}
}
},
"required": [
"model",
"prompt",
"targetSchema"
],
"additionalProperties": false
},
"output": {
"type": "string"
}
},
"required": [
"id",
"onError",
"type",
"document",
"ai",
"output"
],
"additionalProperties": false
}
]
}
}
}
}