# Web Component contract

**Status:** CURRENT, profile version 1.

## Purpose

This specification defines one reviewed interface contract for standards-based
Web Components. It does not render components or own a product workflow.

The installed application in the sibling repository uses the contract for live
component configuration, parameter controls, and variant workspaces.

## Ownership boundary

The specification defines:

- the schema profile and version boundary;
- assignable instance-schema derivation;
- canonical instance documents;
- generation outcomes and limits;
- stable instance identity; and
- application of one instance document to one fresh custom element.

The specification does not define:

- rendering or screenshots;
- component module evaluation;
- project discovery or build processes;
- baseline approval;
- application controls or workspaces; or
- product persistence.

## Schema profile

A supported schema uses these fixed identity fields:

```json
{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "profile": "web-component-contract/schema",
  "profileVersion": 1
}
```

The runtime accepts only profile version 1. It reports the found and expected
versions for a mismatch. It does not decode another profile version.

The schema has `type: "object"` and one valid custom-element `tagName`. Its
`properties` object contains exactly these sections:

- `attributes`;
- `properties`;
- `events`;
- `slots`;
- `cssProperties`; and
- `cssParts`.

Each section is a closed object schema. A member schema uses the supported JSON
Schema Draft 2020-12 keywords and local references. Do not use an external
reference. The reviewed schema must remain self-contained.

## Assignable instance document

Only four sections contain assignable state:

```json
{
  "attributes": {},
  "properties": {},
  "cssProperties": {},
  "slots": {}
}
```

`events` and `cssParts` are descriptive. They do not generate values and do not
call a setter.

Canonical storage sorts each object key and omits no supplied value. It rejects
`undefined`, a function, a symbol, a non-finite number, a cycle, or a host
object. A stable instance identity hashes the profile identity, profile version,
tag name, and canonical instance document.

## Application semantics

Apply a complete instance document to one fresh custom element.

| Section | Operation |
| --- | --- |
| `attributes` | `true` sets an empty attribute. `false` or `null` removes it. Each other value uses its string representation. |
| `properties` | Assign a structured clone directly to the named JavaScript property. |
| `cssProperties` | A non-empty value uses `style.setProperty`. An empty string or `null` removes the property. |
| `slots` | The `default` member creates ordinary light DOM. Each other member creates top-level elements with the matching `slot` attribute. |

Slot text creates a text node. A node record uses `tag`, optional `text`,
optional `attrs`, and optional recursive `children`. Do not use `innerHTML`.

Reject a second application to the same element. Each variant requires a fresh
instance because custom-element state is not part of the instance document.

## Variant generation

Derive one closed JSON Schema from the four assignable sections. Delegate value
combination to SandScript's compiled-schema generation operation.

Pairwise generation is the default. Cartesian and one-wise generation are
explicit alternatives. Every call has a positive maximum-variant bound. Reject
an output that exceeds the bound instead of returning a partial variant set.

A reviewed schema supplies each finite generation domain through defaults,
enumerations, examples, bounds, structured schemas, or explicit generator
configuration. Do not infer arbitrary values from component source.

## Migration

A reviewed component schema is a mutable durable source of truth. Profile
version 1 is the first supported format and has no earlier migration hop.

An implementation rejects each unsupported version. A migration operation
accepts the current version with zero hops and rejects a version for which no
offline hop exists.

A future profile cutover must publish one frozen per-hop migration alongside
the versioned artifacts. It must preserve its input, write a distinct output,
validate before rewriting, and verify the migrated schema and one applied
instance through the current implementation.

## Distribution

The specification, machine-readable profile, and conformance examples are
published at stable versioned URLs. Consumers bundle or pin reviewed artifact
bytes; they do not depend on a mutable website response at runtime. SandScript
owns schema compilation, validation, generation, and contract interpretation.
Sandom publishes these artifacts but provides no contract runtime or adapter.
