Spectral Ruleset
A Spectral ruleset: a portable, machine-readable set of API governance rules applied to JSON or YAML documents. This schema describes the serialized (JSON/YAML) form of the format. See https://github.com/api-commons/spotlight-spec for the specification.
Properties
| Name | Type | Description |
|---|---|---|
| description | string | Human-readable description of what this ruleset governs. |
| documentationUrl | string | URL to documentation for this ruleset. Used as the fallback documentation link for any rule that does not declare its own. |
| formats | object | Document formats this ruleset applies to. Acts as the default for every rule that does not declare its own formats. When omitted, rules apply to every document. |
| extends | object | Other rulesets this ruleset inherits from. |
| rules | object | Map of rule name to rule definition. A rule name is the stable identifier reported in results and used to override the rule downstream. |
| aliases | object | Named, reusable path expressions that rules may reference from `given` with a leading `#`. |
| overrides | object | Per-file and per-location adjustments applied on top of the ruleset. |
| parserOptions | object | Severities for problems detected while parsing the document itself, before any rule runs. |
| functions | array | Names of custom functions to load from `functionsDir`. Serialized rulesets only; JavaScript rulesets import functions directly instead. |
| functionsDir | string | Directory, relative to the ruleset file, that custom functions named in `functions` are loaded from. Defaults to `functions`. |
JSON Schema
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"$id": "https://spec.spotlight-rules.com/schema/v1/spectral-ruleset.schema.json",
"title": "Spectral Ruleset",
"description": "A Spectral ruleset: a portable, machine-readable set of API governance rules applied to JSON or YAML documents. This schema describes the serialized (JSON/YAML) form of the format. See https://github.com/api-commons/spotlight-spec for the specification.",
"type": "object",
"properties": {
"description": {
"type": "string",
"description": "Human-readable description of what this ruleset governs."
},
"documentationUrl": {
"type": "string",
"format": "uri",
"description": "URL to documentation for this ruleset. Used as the fallback documentation link for any rule that does not declare its own."
},
"formats": {
"$ref": "#/$defs/formats",
"description": "Document formats this ruleset applies to. Acts as the default for every rule that does not declare its own formats. When omitted, rules apply to every document."
},
"extends": {
"$ref": "#/$defs/extends",
"description": "Other rulesets this ruleset inherits from."
},
"rules": {
"type": "object",
"description": "Map of rule name to rule definition. A rule name is the stable identifier reported in results and used to override the rule downstream.",
"propertyNames": {
"minLength": 1
},
"additionalProperties": {
"$ref": "#/$defs/rule"
}
},
"aliases": {
"$ref": "#/$defs/aliases",
"description": "Named, reusable path expressions that rules may reference from `given` with a leading `#`."
},
"overrides": {
"$ref": "#/$defs/overrides",
"description": "Per-file and per-location adjustments applied on top of the ruleset."
},
"parserOptions": {
"$ref": "#/$defs/parserOptions",
"description": "Severities for problems detected while parsing the document itself, before any rule runs."
},
"functions": {
"type": "array",
"description": "Names of custom functions to load from `functionsDir`. Serialized rulesets only; JavaScript rulesets import functions directly instead.",
"items": {
"type": "string",
"minLength": 1
}
},
"functionsDir": {
"type": "string",
"description": "Directory, relative to the ruleset file, that custom functions named in `functions` are loaded from. Defaults to `functions`.",
"minLength": 1
}
},
"patternProperties": {
"^x-": true
},
"additionalProperties": false,
"anyOf": [
{ "required": ["extends"] },
{ "required": ["rules"] },
{ "required": ["overrides"] }
],
"$defs": {
"numericSeverity": {
"title": "Numeric severity",
"description": "0 = error, 1 = warn, 2 = info, 3 = hint, -1 = off.",
"enum": [-1, 0, 1, 2, 3]
},
"humanReadableSeverity": {
"title": "Human-readable severity",
"enum": ["error", "warn", "info", "hint", "off"]
},
"severity": {
"title": "Severity",
"description": "How a rule's results are reported. `off` (-1) disables the rule. Defaults to `warn` when unset.",
"oneOf": [
{ "$ref": "#/$defs/numericSeverity" },
{ "$ref": "#/$defs/humanReadableSeverity" }
]
},
"format": {
"title": "Format",
"description": "Identifier of a document format. A format is a predicate that decides whether a given document is of that kind, so a rule scoped to a format only runs against matching documents. The listed values are those registered by the reference implementation; any string is permitted so that new and custom formats remain valid.",
"type": "string",
"minLength": 1,
"anyOf": [
{
"enum": [
"oas2",
"oas3",
"oas3_0",
"oas3_1",
"asyncapi2",
"aas2",
"aas2_0",
"aas2_1",
"aas2_2",
"aas2_3",
"aas2_4",
"aas2_5",
"aas2_6",
"aas3",
"aas3_0",
"arazzo1_0",
"jsonSchema",
"jsonSchemaLoose",
"jsonSchemaDraft4",
"jsonSchemaDraft6",
"jsonSchemaDraft7",
"jsonSchemaDraft2019_09",
"jsonSchemaDraft2020_12"
]
},
{ "type": "string" }
]
},
"formats": {
"title": "Formats",
"type": "array",
"items": { "$ref": "#/$defs/format" }
},
"pathExpression": {
"title": "Path expression",
"description": "Either a JSONPath expression beginning with `$`, or an alias reference beginning with `#` optionally followed by a JSONPath subset (for example `#Info.description`).",
"type": "string",
"minLength": 1,
"anyOf": [
{
"pattern": "^\\$",
"title": "JSONPath expression"
},
{
"pattern": "^#",
"title": "Alias reference"
}
]
},
"arrayGiven": {
"title": "Path expression list",
"type": "array",
"minItems": 1,
"items": { "$ref": "#/$defs/pathExpression" }
},
"given": {
"title": "Given",
"description": "The part or parts of the document a rule is applied to. A single path expression, or an array of them.",
"oneOf": [
{ "$ref": "#/$defs/pathExpression" },
{ "$ref": "#/$defs/arrayGiven" }
]
},
"functionInvocation": {
"title": "Function invocation",
"description": "The assertion half of a rule: the function to run against each node matched by `given`, and the options it takes.",
"type": "object",
"properties": {
"field": {
"type": "string",
"description": "Narrow the assertion to a single property of the matched node, rather than the node itself. `@key` targets the node's own key."
},
"function": {
"type": "string",
"minLength": 1,
"description": "Name of a core function (`alphabetical`, `casing`, `defined`, `enumeration`, `falsy`, `length`, `pattern`, `schema`, `truthy`, `undefined`, `unreferencedReusableObject`, `xor`, `or`) or of a custom function declared in `functions`."
},
"functionOptions": {
"type": "object",
"description": "Options passed to the function. The accepted shape is defined by the function itself."
}
},
"required": ["function"]
},
"then": {
"title": "Then",
"description": "One assertion, or an array of assertions all applied to the nodes matched by `given`.",
"oneOf": [
{ "$ref": "#/$defs/functionInvocation" },
{
"type": "array",
"minItems": 1,
"items": { "$ref": "#/$defs/functionInvocation" }
}
]
},
"ruleDefinition": {
"title": "Rule definition",
"description": "A complete rule: where to look (`given`) and what must hold there (`then`).",
"type": "object",
"properties": {
"description": {
"type": "string",
"description": "Human-readable statement of what the rule requires."
},
"documentationUrl": {
"type": "string",
"format": "uri",
"description": "URL explaining the rule and how to satisfy it. Reported alongside results."
},
"message": {
"type": "string",
"description": "Template for the reported message. Supports the placeholders `{{error}}`, `{{description}}`, `{{path}}`, `{{property}}`, and `{{value}}`."
},
"severity": {
"$ref": "#/$defs/severity",
"description": "Severity of this rule's results. Defaults to `warn`."
},
"formats": {
"$ref": "#/$defs/formats",
"description": "Document formats this rule applies to. Overrides the ruleset-level `formats`."
},
"given": {
"$ref": "#/$defs/given"
},
"then": {
"$ref": "#/$defs/then"
},
"recommended": {
"type": "boolean",
"description": "Whether the rule is enabled when a consumer extends this ruleset in `recommended` mode. Defaults to true."
},
"resolved": {
"type": "boolean",
"description": "Whether the rule runs against the document with `$ref`s resolved (true, the default) or against the raw authored document (false). Set to false for rules about references themselves."
},
"tags": {
"type": "array",
"description": "Free-form labels for grouping and filtering rules.",
"items": { "type": "string" }
},
"type": {
"description": "Coarse classification of the rule. `validation` rules assert correctness; `style` rules assert convention.",
"enum": ["style", "validation"]
},
"extensions": {
"type": "object",
"description": "Arbitrary consumer-defined metadata carried with the rule and ignored by the engine."
}
},
"required": ["given", "then"],
"patternProperties": {
"^x-": true
},
"additionalProperties": false
},
"rule": {
"title": "Rule",
"description": "A full rule definition, or — when adjusting a rule inherited via `extends` — a severity string, or a boolean where false disables the rule and true restores its declared severity.",
"oneOf": [
{ "$ref": "#/$defs/ruleDefinition" },
{ "$ref": "#/$defs/humanReadableSeverity" },
{ "type": "boolean" }
]
},
"extendsEntry": {
"title": "Extends entry",
"description": "A reference to another ruleset: a built-in (`spectral:oas`, `spectral:asyncapi`, `spectral:arazzo`), a file path, an npm module, or a URL.",
"type": "string",
"minLength": 1
},
"extendsTuple": {
"title": "Scoped extends entry",
"description": "A ruleset reference paired with the set of its rules to enable: `recommended` (the default), `all`, or `off`.",
"type": "array",
"prefixItems": [
{ "$ref": "#/$defs/extendsEntry" },
{ "enum": ["all", "recommended", "off"] }
],
"minItems": 2,
"items": false
},
"extends": {
"title": "Extends",
"oneOf": [
{ "$ref": "#/$defs/extendsEntry" },
{
"type": "array",
"items": {
"oneOf": [
{ "$ref": "#/$defs/extendsEntry" },
{ "$ref": "#/$defs/extendsTuple" }
]
}
}
]
},
"aliasTarget": {
"title": "Alias target",
"description": "The path expressions an alias resolves to for one set of formats.",
"type": "object",
"properties": {
"formats": { "$ref": "#/$defs/formats" },
"given": { "$ref": "#/$defs/arrayGiven" }
},
"required": ["formats", "given"]
},
"scopedAlias": {
"title": "Scoped alias",
"description": "An alias that resolves to different path expressions depending on the format of the document being linted.",
"type": "object",
"properties": {
"description": {
"type": "string",
"description": "Human-readable purpose of the alias."
},
"targets": {
"type": "array",
"minItems": 1,
"items": { "$ref": "#/$defs/aliasTarget" }
}
},
"required": ["targets"]
},
"alias": {
"title": "Alias",
"description": "Either a list of path expressions, or a scoped alias that varies by format.",
"if": { "type": "object" },
"then": { "$ref": "#/$defs/scopedAlias" },
"else": { "$ref": "#/$defs/arrayGiven" }
},
"aliases": {
"title": "Aliases",
"type": "object",
"propertyNames": {
"pattern": "^[A-Za-z][A-Za-z0-9_-]*$"
},
"additionalProperties": { "$ref": "#/$defs/alias" }
},
"parserOptions": {
"title": "Parser options",
"type": "object",
"properties": {
"duplicateKeys": {
"$ref": "#/$defs/severity",
"description": "Severity for duplicate keys found in the document. Defaults to `error`."
},
"incompatibleValues": {
"$ref": "#/$defs/severity",
"description": "Severity for YAML values that cannot be represented in JSON. Defaults to `error`."
}
},
"additionalProperties": false
},
"overrides": {
"title": "Overrides",
"description": "Ordered list of adjustments. Later matching entries win over earlier ones, and every override wins over the base ruleset.",
"type": "array",
"minItems": 1,
"items": { "$ref": "#/$defs/override" }
},
"override": {
"title": "Override",
"description": "An adjustment scoped by `files`. When every glob in `files` carries a JSON Pointer fragment (`path/to/file.yaml#/paths/~1users`), the override may only change rule severities. Otherwise it may change anything a ruleset can declare.",
"type": "object",
"required": ["files"],
"if": {
"type": "object",
"required": ["files"],
"properties": {
"files": {
"type": "array",
"minItems": 1,
"items": {
"type": "string",
"minLength": 1,
"pattern": "^[^#]+#"
}
}
}
},
"then": {
"title": "Pointer-scoped override",
"type": "object",
"properties": {
"files": true,
"rules": {
"type": "object",
"additionalProperties": { "$ref": "#/$defs/severity" }
}
},
"required": ["rules"],
"additionalProperties": false
},
"else": {
"title": "File-scoped override",
"allOf": [
{
"type": "object",
"required": ["files"],
"properties": {
"files": {
"type": "array",
"minItems": 1,
"items": {
"type": "string",
"minLength": 1,
"pattern": "[^#]"
}
}
}
},
{
"type": "object",
"properties": {
"files": true,
"formats": { "$ref": "#/$defs/formats" },
"extends": { "$ref": "#/$defs/extends" },
"rules": {
"type": "object",
"additionalProperties": { "$ref": "#/$defs/rule" }
},
"parserOptions": { "$ref": "#/$defs/parserOptions" },
"aliases": { "$ref": "#/$defs/aliases" }
},
"anyOf": [
{ "required": ["extends"] },
{ "required": ["rules"] }
]
}
]
}
}
}
}
Work with this as data
Every JSON Schema here is available over the APIs.io API and to AI agents over MCP.
MCP server
One button, every client — Claude, Cursor, VS Code and the rest.
https://apis.io/mcp
Tools for schemas
4 MCP tools reach this
find_json_schemasBrowse and filter every JSON Schema in the catalog.apis_io_searchSTART HERE — APIs, providers and tags for one query, each with its total.resolveTurn a domain, URL or GitHub org into the provider it belongs to.find_cohortsEvery scored population of providers in the catalog.
Call it yourself
curl for this page
curl "https://apis.io/api/v1/json-schemas/spotlight-rules-spectral-ruleset.schema"
curl "https://apis.io/api/v1/json-schemas?limit=25"
Discovery needs no key. Ratings and market analysis are Pro.
Get an API key
Free tier, no form to fill in. Signing in shares your email address with us — we store it to create your key and to recognise you if you sign in with another provider. See our Privacy Policy and Terms.
A second provider on the same verified email joins the account you already have.