Schemas

A Schema defines the structure and validation rules for your business data. Built on the open JSON Schema standard, schemas ensure every piece of data entering a workflow is valid and consistent.

Schemas are the starting point of every SignStack workflow. You define your data first — employee, company, deal_info — and everything else flows from it. Templates render your data into documents. Blueprints orchestrate workflows around it. But it all begins with the schema.

YAML Format

apiVersion: signstack/v1beta2
kind: Schema

metadata:
  key: employee                       # Required, snake_case
  version: 1.0.0                      # Required, semver
  name: Employee                      # Required
  description: Employee data for HR documents
  labels:
    domain: hr

spec:
  jsonSchemaDraft: 2020-12            # Required: 2020-12, 2019-09, draft-07, draft-06, draft-04
  file: ./definitions/employee.json   # Path to JSON Schema (or use `schemaDefinition:` for inline)

Metadata Fields

Field Required Description
key Yes Unique identifier (snake_case). Referenced as key@version by other resources.
version Yes Semantic version (1.0.0) or draft.
name Yes Human-readable name (max 200 chars).
description No Description of the schema's purpose (max 1000 chars).
labels No Key-value pairs for categorization and filtering. Keys must be snake_case.

Spec Fields

Field Required Description
jsonSchemaDraft Yes JSON Schema draft version. Use 2020-12 for new schemas.
file One of file / schemaDefinition Relative path to a .json file containing the JSON Schema definition. Convention: ./definitions/<name>.json.
schemaDefinition One of file / schemaDefinition Inline JSON Schema definition as a YAML object. Useful for small schemas or when you don't want a separate .json file.

Examples

Minimal Schema (Inline)

apiVersion: signstack/v1beta2
kind: Schema

metadata:
  key: contact
  version: 1.0.0
  name: Contact

spec:
  jsonSchemaDraft: 2020-12
  schemaDefinition:
    type: object
    properties:
      name:  { type: string }
      email: { type: string, format: email }
    required: [name, email]
apiVersion: signstack/v1beta2
kind: Schema

metadata:
  key: employee
  version: 1.0.0
  name: Employee
  description: Employee data for HR documents
  labels:
    domain: hr

spec:
  jsonSchemaDraft: 2020-12
  file: ./definitions/employee.json

With ./definitions/employee.json:

{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "type": "object",
  "properties": {
    "firstName": { "type": "string" },
    "lastName": { "type": "string" },
    "email": { "type": "string", "format": "email" },
    "phone": { "type": "string" },
    "department": { "type": "string" },
    "tier": {
      "type": "string",
      "enum": ["Standard", "Premium", "Enterprise"],
      "description": "Subscription tier affecting discount rates"
    },
    "startDate": { "type": "string", "format": "date" }
  },
  "required": ["firstName", "lastName", "email"]
}

Multiple Schemas in One File

Use YAML multi-document syntax (---) to define multiple schemas in a single file:

apiVersion: signstack/v1beta2
kind: Schema

metadata:
  key: employee
  version: 1.0.0
  name: Employee

spec:
  jsonSchemaDraft: 2020-12
  file: ./definitions/employee.json

---
apiVersion: signstack/v1beta2
kind: Schema

metadata:
  key: company
  version: 1.0.0
  name: Company

spec:
  jsonSchemaDraft: 2020-12
  file: ./definitions/company.json

How Schemas Are Used

Schemas are referenced by templates and blueprints as key@version:

# In a template
inputs:
  - key: employee
    schema: employee@1.0.0

# In a blueprint
inputs:
  - key: employee
    schema: employee@1.0.0

When a workflow runs, entity data provided for each input is validated against the referenced schema. Invalid data is rejected with a validation error.

In JSONata Expressions

Once entities are in the workflow, you reference them by their input key:

$.employee.firstName              # Simple property access
$.employee.tier = "Enterprise"    # Conditional check
$.deal.value * 0.05               # Calculations across entities

JSON Schema Drafts

Draft Use Case
2020-12 Latest features, recommended for new schemas
2019-09 Vocabulary system, good backwards compatibility
draft-07 Widely supported, includes if/then/else
draft-06 Added const and contains
draft-04 Maximum compatibility with legacy systems

Versioning

Schemas use semantic versioning. A schema moves from Draft to a concrete published version (1.0.0); to make further changes, you cut a new version (1.1.0, 2.0.0). Published versions are immutable — every workflow running against 1.0.0 keeps validating against the exact shape it was designed for, even after 2.0.0 ships.

Draft → 1.0.0 (published, immutable)
          ↓ edit + publish
        1.1.0 (published, immutable)
          ↓ edit + publish
        2.0.0 (published, immutable)

Pick the version bump based on the change:

  • MAJOR (2.0.0) — Breaking changes (removed required fields, type changes)
  • MINOR (1.1.0) — Backwards-compatible additions (new optional field)
  • PATCH (1.0.1) — Bug fixes (description update, regex correction)

Best Practices

  1. Design for reuse — Create schemas for core business concepts (employee, deal_info, property), not document-specific fields. The same schema should power multiple templates.
  2. Use meaningful keys — Schema keys appear in expressions ($.employee.firstName). Keep them readable: client_info not ci_v2.
  3. Add descriptions — Descriptions help your team and AI tools generate better primitives from your data models.
  4. Plan for evolution — Use semantic versioning. Published versions are immutable, so existing workflows keep running against the schema they were designed for; cut a new version when you need to change shape.