ObjectDefinition
Concept: Objects, Records, and Fields →
The parsed contents of a *_object.json5 file: an object declaration.
Properties
Section titled “Properties”| Property | Type | Required/Default | Constraints | Meaning |
|---|---|---|---|---|
objectKey |
string | Required | min length 1; max length 63; pattern ^[A-Z][a-zA-Z0-9]*$ |
The object’s identifier within its module. |
label |
string | Required | Human-readable display name for the object type — shown in Studio object lists, breadcrumbs, and API documentation. | |
description |
string | Optional | Free-text description of the object’s purpose, shown in Studio and API docs. | |
extends |
string | Optional | The fully qualified name of the parent object to extend, e.g. "core.Party". |
|
abstract |
boolean | Optional (default: false) |
Whether the object is abstract. | |
extensionKind |
enum (ExtensionKind) |
Optional | Controls the inheritance mode. | |
identity |
IdentityConfig object |
Optional | Visual identity (color and icon) for the object, used by Studio to render object lists, breadcrumbs, and record badges. | |
seed |
SeedDefinition object |
Optional | rejected by the metadata loader when authored in a file-based *_object.json5 (redirects to a separate *_seed.json5 file); Rust-native builtin objects are excepted | Deprecated inline location for seed data. |
rules |
object | Optional (default: {}) |
Object-level validation rules, keyed by rule name. | |
labelField |
string | Optional | min length 1; max length 63; pattern ^[a-z][a-zA-Z0-9]*$ |
The field whose value is used as the human-readable label for records of this object — for example, showing a Contact’s name field value in place of its ID wherever the record is referenced. |
objectKey
Section titled “objectKey”The object’s identifier within its module.
PascalCase, [A-Z][a-zA-Z0-9]*, no underscore — for example
Account, Contact, OrderLineItem. Must be unique within the
module. Combined with the module key to form the fully qualified
name (e.g. core.Account).
Human-readable display name for the object type — shown in Studio object lists, breadcrumbs, and API documentation.
This is the label of the type itself, not a per-record label. For
the field whose value is used as the human-readable label for
individual records, see labelField.
description
Section titled “description”Free-text description of the object’s purpose, shown in Studio and API docs. Absent by default.
extends
Section titled “extends”The fully qualified name of the parent object to extend, e.g.
"core.Party". Absent by default — the object has no parent and
does not participate in inheritance.
When set, this object inherits all fields from the parent and its
ancestors, and its primary key references the parent object’s
table instead of the universal root table (hf_object).
abstract
Section titled “abstract”Whether the object is abstract. Default false.
When true, the object cannot be instantiated directly through
the data API — create requests for it are rejected. Abstract
objects exist only as base types in an inheritance hierarchy.
When false, the object can be created directly.
extensionKind
Section titled “extensionKind”Controls the inheritance mode. Required when extends is set; has
no effect otherwise. See ExtensionKind for the two values.
identity
Section titled “identity”Visual identity (color and icon) for the object, used by Studio to render object lists, breadcrumbs, and record badges.
Both subfields are optional; when absent, Studio falls back to
platform defaults at render time. See IdentityConfig.
Deprecated inline location for seed data. Not accepted when
authoring an *_object.json5 file — the loader rejects any object
file that sets this key, naming the correct *_seed.json5 file
path in its diagnostic. Author seed data in a separate
<moduleKey>_<ObjectKey>_seed.json5 file instead; see
SeedDefinition.
Object-level validation rules, keyed by rule name.
Each rule carries a label, a boolean formula expression, and an
optional user-facing violation message; see ValidationRule. The
expression is checked against the object’s fields when metadata is
compiled, and re-checked against each record at write time.
Duplicate rule names within one *_object.json5 file: the last
occurrence wins (standard JSON5 parsing behavior).
labelField
Section titled “labelField”The field whose value is used as the human-readable label for
records of this object — for example, showing a Contact’s name
field value in place of its ID wherever the record is referenced.
When absent, this object defers to the nearest ancestor’s
labelField in the inheritance chain. When no object in the
chain declares one, records of this type have no label.
ExtensionKind
Section titled “ExtensionKind”Controls how a derived object’s records relate to other subtypes of the
same parent when it declares extends.
Required when extends is set; has no effect otherwise.
| Value | Status | Description |
|---|---|---|
subtype |
Exclusive subtype. | |
aspect |
Stackable aspect. |
IdentityConfig
Section titled “IdentityConfig”Visual identity (color and icon) for a module or object.
Both fields are optional; when absent, Studio falls back to platform defaults at render time.
| Property | Type | Required/Default | Constraints | Meaning |
|---|---|---|---|---|
color |
enum (IdentityHue) |
Optional | The identity hue. | |
icon |
string | Optional | A Phosphor icon name in PascalCase, matching the icon’s export name from @phosphor-icons/react (e.g. "Cube", "Lock", "MagnifyingGlass"). |
The identity hue. Absent by default (platform default hue).
A Phosphor icon name in PascalCase, matching the icon’s export
name from @phosphor-icons/react (e.g. "Cube", "Lock",
"MagnifyingGlass"). Absent by default (platform default icon).
Must be one of the curated icon set the platform ships with — an unrecognized name is rejected when the manifest loads.
IdentityHue
Section titled “IdentityHue”One of nine curated colors for module and object visual identity.
Written in kebab-case in *_module.json5 and *_object.json5
manifests (e.g. color: "indigo"). See IdentityConfig.
| Value | Status | Description |
|---|---|---|
blue |
Blue — the recommended default for foundational modules. | |
cloud |
Cloud — soft pale blue for ambient or utility surfaces. | |
electric |
Electric — saturated cyan for high-energy contexts. | |
indigo |
Indigo — deep blue-violet for analytic or data surfaces. | |
purple |
Purple — for collaboration and people-centric modules. | |
violet |
Violet — a softer, magenta-leaning purple. | |
teal |
Teal — for operational or process-centric modules. | |
green |
Green — for success, lifecycle, or billing flows. | |
orange |
Orange — for warnings, sales, or time-sensitive flows. |
SeedAccess
Section titled “SeedAccess”Who controls this seed data, and how mutable it is at runtime.
| Value | Applied | Runtime mutability |
|---|---|---|
vendor |
Every apply | Immutable — API writes rejected |
module |
Every apply | Immutable — API writes rejected |
architect |
Every apply | Immutable — API writes rejected |
user |
Once, on first apply | Fully mutable |
| Value | Status | Description |
|---|---|---|
vendor |
Platform vendor. | |
module |
Module developer. | |
architect |
Deploying architect. | |
user |
Initial state only. |
SeedDefinition
Section titled “SeedDefinition”The parsed contents of a *_seed.json5 file: pre-populated records for
one object.
Declares records that the apply engine upserts (or inserts once, for
user access) alongside DDL convergence. Records are matched against
existing rows by the natural key declared in key, so re-applying the
same file is idempotent.
{ access: "vendor", key: "code", data: [ { code: "USD", name: "US Dollar", symbol: "$", decimalPlaces: 2 }, { code: "EUR", name: "Euro", symbol: "€", decimalPlaces: 2 }, ],}| Property | Type | Required/Default | Constraints | Meaning |
|---|---|---|---|---|
access |
enum (SeedAccess) |
Required | Who controls this seed data and how mutable it is at runtime. | |
key |
string | Required | The natural key field(s) used to match seed records against existing rows. | |
data |
array of any | Optional | The seed records, inline. | |
file |
string | Optional | Path to an external JSON5 file holding the seed records, for datasets too large to inline comfortably. | |
delete |
array of any | Optional | Natural key values identifying records to remove on the next apply. |
The seed records, inline.
Each entry is a JSON object whose keys match the object’s field
keys. System fields (id, createdAt, updatedAt, objectType,
ownerId) are populated automatically and must not appear here.
Mutually exclusive with file — a *_seed.json5 file sets exactly
one of the two.
Path to an external JSON5 file holding the seed records, for datasets too large to inline comfortably.
Relative to the directory containing the *_seed.json5 file. The
target file’s top-level value must be a bare JSON5 array of record
objects, shaped exactly like data entries. Mutually exclusive
with data — setting both is a loader error. The target file’s
name must not end in a reserved metadata suffix (_module,
_object, _field, _relationship, _seed) followed by
.json5, or the loader would try to parse it as a metadata
definition instead of a plain data file.
delete
Section titled “delete”Natural key values identifying records to remove on the next apply.
Each entry uses the same shape as a key value, identifying an
existing record for deletion rather than upsert.
ValidationRule
Section titled “ValidationRule”A single entry in an object’s rules: block: a named boolean condition
that every record of the object must satisfy.
Carries a human-readable label, a formula expression evaluated as a
boolean predicate, and optional fields controlling the violation
message and which field an error is attributed to.
| Property | Type | Required/Default | Constraints | Meaning |
|---|---|---|---|---|
label |
string | Required | Human-readable name for the rule, shown in error displays. | |
expression |
string | Required | The rule’s boolean formula expression, e.g. "score >= 0". |
|
message |
string | Optional | The message shown to the caller when a record violates this rule, e.g. "Score cannot be negative.". |
|
field |
string | Optional | min length 1; max length 63; pattern ^[a-z][a-zA-Z0-9]*$ |
Pins which field a violation of this rule is attributed to in the API error payload. |
Human-readable name for the rule, shown in error displays.
Distinct from the rule’s key in the rules: map — the label may
contain spaces and punctuation. Purely informational; not used to
identify the rule internally.
expression
Section titled “expression”The rule’s boolean formula expression, e.g. "score >= 0". See
the formula language reference for supported syntax.
Must be non-empty and must evaluate to a boolean. An empty expression, one that fails to compile, or one that evaluates to a non-boolean type each produce a compile-time diagnostic.
message
Section titled “message”The message shown to the caller when a record violates this rule,
e.g. "Score cannot be negative.". Absent by default.
When absent, a generic message derived from label is used
instead. When set, this string is returned verbatim in the API
error payload.
Pins which field a violation of this rule is attributed to in the API error payload. Absent by default.
When absent, attribution is derived automatically: an expression
that references exactly one field on this object attributes to
that field; anything else (multiple fields, a cross-object
reference, or a constant expression) attributes to the object as a
whole (__object). When set, the field must exist on the object
and appear in the expression — an invalid pin produces a
compile-time diagnostic and falls back to whole-object
attribution.
Read-only (server-set)
Section titled “Read-only (server-set)”These are computed or managed by the server. They appear in API responses but are rejected or ignored in request bodies — they do not appear in the property table above.
| Property | Meaning |
|---|---|
ownedByRelationship |
When set, this object is a managed junction table generated automatically by a relationship, rather than a directly-authored object. |
Example
Section titled “Example”{ "label": "example", "objectKey": "example"}