# Schemas
A schema describes the shape of a value: its type, its constraints, and enough labelling for a client to
build a form from it. The framework speaks [JSON Schema](https://json-schema.org), and an entity class
**generates its own schema** from the documentation of its properties — you annotate the class, you do not
write the schema by hand.
## Model JSON serialization
```json
{UID}: {
"$": {CLASS},
"$id": {UID},
{PROPERTY}: {DATA},
..
}
```
`$` carries the class (or the factory function) an entry has to be rebuilt with — see
[Serialization](Serialization.md).
## Model schema
```json
"$defs": {
{CLASS}: {
"type": "object",
{PROPERTY}: {SCHEMA},
..
},
{CHILD CLASS}: {..},
..
}
```
## Documenting a class
```
@hash {CLASS}xx{PROPERTY1}xx{PROPERTY2}
@uid {CLASS}xx{PRIMARY}
```
`{CLASS}` is replaced by the entity's class, `{PROPERTY1}` by the value of that property.
- a **hash** is generated without any primary key, so an entity can be found without knowing its id;
- a **uid** is generated from the primary key(s) and is unique across every entity;
- if `@hash` or `@uid` is `auto`, `uid()`/`hash()` must be reimplemented, and the schema will not validate
those values.
## Documenting a property
```
@type {TYPE}
@{CONSTRAINT} {VALUE}
@internal
```
`@internal` keeps a property out of the generated schema.
### Simple types
```
@type integer|number|string|boolean|null|const
```
### Constant type
A class constant is automatically turned into `@type const`.
### Class types
`@type {CLASS}` builds the schema straight from that php class:
```json
"type": {"$ref": "#$defs/{CLASS}"}
```
### Enum type
`@type enum[...{TYPE}]`, where `{SCHEMA}` is the schema of `{TYPE}`:
```json
"enum": [...{SCHEMA}]
```
### Array type
`@type [{TYPE}]`:
```json
"type": "array",
"items": {SCHEMA}
```
`@var` also reads phpstan's arrays: `list<{TYPE}>`, `array<{TYPE}>`, `array`, `iterable<{TYPE}>` and
`{TYPE}[]` are this list; `array` is a map (`"type": "object", "additionalProperties": {SCHEMA}`);
`array` is a list of anything. `?list<{TYPE}>` / `list<{TYPE}>|null` may also be null.
### Object type
`@type {{ID}: {CLASS}}` — `{ID}` is a property name in `{CLASS}`:
```json
"type": "object",
"additionalProperties": {SCHEMA}
```
### Complex types
```
not({TYPE})
anyOf(...{TYPE})
oneOf(...{TYPE})
allOf(...{TYPE})
```
### Constraints
Any JSON Schema constraint can be used as an annotation: `@maxLength 3`, `@minimum 0`, `@format email`.
---
# Keyword reference
## Types
`type` is a string or an array of strings: `{"type": "number"}`, `{"type": ["number", "string"]}`.
| type | php value |
|---|---|
| `string` | string |
| `integer` | int |
| `number` | float |
| `boolean` | bool |
| `null` | null |
| `instance` | object |
| `object` | array |
| `array` | array with only numerical indexes (a list) |
## Information
These describe a value rather than constrain it; a client builds its forms and tables out of them.
| keyword | value | |
|---|---|---|
| `$id` | string | a unique url for this schema |
| `label` | string | short descriptive title |
| `title` | string | descriptive title |
| `description` | string | longer explanation of the data the schema describes |
| `default` | any | a default value |
| `order` | integer | where the property sorts among its siblings |
| `icon` | string | an icon name, or a utf-8 character |
| `readOnly` | boolean | |
| `examples` | array | values that validate against the schema |
| `$comment` | string | a note; never used for validation |
| `$links` | object | links to reach the data this schema describes |
| `api` | | the link to interact with the data api |
| `index` | | the link listing the resources available in the api |
## Constraints
### string
| keyword | value | |
|---|---|---|
| `minLength` | integer | |
| `maxLength` | integer | |
| `pattern` | string | regular expression, ECMA 262 syntax |
| `format` | string | `date`, `date-time`, `uri`, `email`, `hostname`, `ipv4`, `ipv6`, `regex` |
### integer / number
| keyword | value | |
|---|---|---|
| `multipleOf` | number | |
| `minimum` | number | `>=` |
| `exclusiveMinimum` | number | `>` |
| `maximum` | number | `<=` |
| `exclusiveMaximum` | number | `<` |
### object
| keyword | value | |
|---|---|---|
| `minProperties` | integer | |
| `maxProperties` | integer | |
| `required` | array of string | property names that must be present |
| `dependentRequired` | object | properties required once the keyed property is present |
| `dependentSchemas` | object | schema to apply once the keyed property is present |
| `properties` | object | property name to schema |
| `patternProperties` | object | schema to apply when a property name matches the key (a regex) |
| `additionalProperties` | schema | schema for properties `properties` does not describe |
| `propertyNames` | schema | schema applied to the property names themselves |
| `unevaluatedProperties` | schema | schema for properties no branch evaluated, `anyOf`/`allOf` included |
### array
| keyword | value | |
|---|---|---|
| `minItems` | integer | |
| `maxItems` | integer | |
| `uniqueItems` | boolean | every item must be unique |
| `items` | schema | schema applied to the list's items |
| `prefixItems` | array of schema | schema applied to the item at that index |
| `contains` | schema | applied to between `minContains` (or 1) and `maxContains` (or 1) items |
| `minContains` | integer | |
| `maxContains` | integer | |
| `unevaluatedItems` | schema | schema for items no branch evaluated, `anyOf`/`allOf` included |
### instance
| keyword | value | |
|---|---|---|
| `instanceOf` | array of string | the object must be an instance of at least one of these classes |
### combining
| keyword | value | |
|---|---|---|
| `enum` | array | the value must deeply equal one item |
| `const` | any | the value must deeply equal this |
| `allOf` | array of schema | must validate all of them |
| `anyOf` | array of schema | must validate at least one |
| `oneOf` | array of schema | must validate exactly one |
| `not` | schema | must **not** validate |
| `if` | schema | when it validates, `then` applies; otherwise `else` does |
| `then` | schema | |
| `else` | schema | |
## References
### See also
- [Entities](Entities.md)
- [Serialization](Serialization.md)
- <@\MMO\core\schemas\*>
## Tags
<#schema>, <#validation>