Authoring context

The authoring context is what a host hands an agent so it can answer a question with a composition: the composition contract, what it may compose from, and what it can request by id. It is the untrusted path's other half — the agent writes JSON, and runtime.parse decides whether that JSON is a composition this runtime can render.

const { schema, primitives, views } = runtime.getAuthoringContext();
		
Field What it is Freshness
schema Authoring JSON Schema for a Composition built from this runtime's primitives cached
primitives One catalog entry per primitive: purpose, useWhen, avoidWhen, example cached
views Registered-view summaries, each with its input JSON Schema, read from this runtime's own viewRegistry — the views option to createIsomerRuntime or runtime.viewRegistry.register, never a separately constructed registry live
groups Every pack's primitive groups, in pack order, for an index catalog cached
schemaFor(types) Authoring JSON Schema restricted to types, e.g. a registered view's narrower input uncached
describePrimitives(types) The catalog entries of types and the $defs of schema they reach, with the body-node union stubbed uncached

Both halves arrive from one call on purpose. An agent choosing between routing to a registered view and composing from primitives needs to see both options at once, and a host should not have to stitch that catalog together from two sources.

The caching split is equally deliberate. The schema and catalog cannot change for the runtime's lifetime, and projecting a discriminated union is expensive, so they are computed once via the SDK's buildAuthoringJsonSchema. The view list is read on every call, because a host may register views after boot and an agent asking now should see what is registered now; each view's summary is projected once at registration, so the read is cheap. schemaFor is not cached: it exists for a handful of subsets, not one call per render.

A runtime with many primitives can hand an agent an index built from primitives and groups instead of the whole catalog and schema, then answer each lookup with describePrimitives. Its $defs keep the ids schema uses, so two lookups never disagree about a shared def. Both lookups throw UNKNOWN_PRIMITIVE_TYPE for a type this runtime does not register.

Pass authoring on createIsomerRuntime to name pack-owned $defs (actionItem, badgeItem), attach refine descriptions, or hide a legacy alias. The validator schema parse uses is unchanged. A pack can contribute its own describe/omitProperties too, via authoring on its PrimitivePackInput — see Packs — and the runtime merges every composed pack's contribution with this option, which wins on conflict.

const parsed = runtime.parse(JSON.parse(modelOutput));
if (!parsed.valid) {
  return retryWith(parsed.errors);
}
render(parsed.composition!);
		

parse answers one question — is this a Composition for this runtime? — and stops there. It runs the schema but not the semantic passes, so a composition with two nodes sharing an id parses as valid. If you want those checks, run validate on the parsed composition:

import { warningsForSurface } from '@elastic/isomer-sdk';

const result = runtime.validate(parsed.composition!);
result.errors;
result.warnings;
		
  1. duplicate ids
  2. per-surface findings — narrow with warningsForSurface

Errors from either are path-prefixed and single-purpose, which is the shape a model can retry from.

The runtime supplies the structural half. Most hosts send more, because a vocabulary has copy the runtime does not own: a pack's authoring guide and rules, golden composition fixtures, and runtime.getCapabilities() so an agent stops proposing primitives the host would only degrade.

runtime.getCapabilities();
// { primitives: […], formats: ['react','html','text','markdown','slack','svg'],
//   enhancements: { tableSort: true, clipboard: true } }
		
  1. request them with enhancements: ['tableSort']

formats reports the surfaces that were actually built — a runtime with no frame truthfully omits svg.

View registry for the trusted path · Surfaces for rendering what comes back