Reference
Field Types Every field type you can declare on an object — what it stores, what options it accepts, how it surfaces in REST, Console, and the AI Builder.
53 built-in field types, grouped by family. The full Zod schema is in
packages/spec/src/data/field.zod.ts — this page is a working summary.
Property Type Default Purpose namestring (snake_case) — Machine identifier — REST path segment, SQL column labelstring — Display label in Console typeFieldType — See type tables below requiredboolean falseNOT NULL constraint uniqueboolean falseUnique index searchableboolean falseIndexed for /api/v1/search multipleboolean falseStore an array of values defaultValueunknown — Initial value (literal or CEL) columnNamestring = name Override physical DB column hiddenboolean falseHide from default Console views readonlyboolean falseDisable in forms systemboolean falseAuto-injected (id, created_at, …) indexboolean falseCreate a DB index externalIdboolean falseEligible for upsert via external key inlineHelpTextstring — Tooltip / helper text conditionalRequiredP predicate— Required when CEL is true auditTrailboolean falseTrack every change in audit log encryptionConfigobject — Field-level encryption (see Security ) maskingRulestring — PII masking pattern
Type Use for Key options textshort strings maxLength, minLengthtextareamulti-line maxLengthemailemail format-validated; lowercased urlURL format-validated phonephone E.164 passwordsecrets hashed; never returned by GET markdownmarkdown body rendered in Console preview htmlsanitised HTML DOMPurify on write richtextWYSIWYG Console editor + serialised JSON
Type Use for Key options numberfloats min, max, precision, scalecurrencymoney currencyConfig: { precision, currencyMode: 'fixed' | 'dynamic', defaultCurrency }percent0–100 % min, max, scale
integer and decimal aren't separate types — use number with
scale: 0 for integer, precision+scale for fixed decimal.
Type Stores Notes datecalendar date no timezone datetimeinstant UTC timewall-clock time no date
Type Notes booleanCheckbox toggleSame as boolean, switch UI
Type Notes selectSingle choice — options declared inline or referenced from a picklist multiselectMany choices, stored as an array radioUI alias for select with radio rendering checkboxesUI alias for multiselect with checkbox rendering
Options shape:
options : [
{ value: 'low' , label: 'Low' },
{ value: 'high' , label: 'High' , color: '#e02' },
{ value: 'urgent' , label: 'Urgent' , color: '#c00' }
]
Type Cardinality Semantics lookupmany-to-one Loose reference; deleting the parent doesn't delete the child by default master_detailmany-to-one, cascading Child cannot exist without parent; permissions inherit from parent treeself-reference Hierarchical (parent_id on the same object)
Common options:
{
type : 'lookup' ,
reference : 'account' , // target object name
referenceFilters : [ 'status:active' ], // narrow the lookup picker
deleteBehavior : 'set_null' // 'set_null' | 'cascade' | 'restrict'
}
Type What it does Key option formulaDerived value, evaluated on read or recalc expression: F\record.qty * record.unit_price`` — see CEL summaryRoll-up over a child relation summaryOperations: { object, field, function } (count | sum | avg | min | max)autonumberAuto-incrementing display number format (e.g. TKT-{0000}), startAt
Formula example:
{
name : 'profit_margin' ,
type : 'formula' ,
expression : F `(record.revenue - record.cost) / record.revenue * 100`
}
Type Use for Key option imageimage attachments fileAttachmentConfig (see below)fileany file same avatarprofile pictures square crop, sensible defaults videovideo uploads duration + thumbnail capture audioaudio waveform preview
fileAttachmentConfig : {
maxSize : 10_000_000 , // bytes
allowedTypes : [ 'image/png' , 'image/jpeg' ],
virusScan : true ,
storageProvider : 's3' , // see Configure → Storage
imageValidation : { minWidth : 200 , maxWidth : 4096 , generateThumbnails : [ 'sm' , 'md' , 'lg' ] }
}
Type Stores Notes jsonarbitrary JSON Stored as JSONB on Postgres compositesub-record with named fields Inline struct, not a separate table repeaterarray of composite values One-to-many without a child object
Type Notes locationlat/long + accuracy addressstreet / city / region / postal / country codesource-code field — language, theme, lineNumbers colorcolorFormat: 'hex' | 'rgb' | 'rgba' | 'hsl', presetColors[]rating1–N stars — max, icon sliderbounded number with slider UI signaturedrawn signature, stored as image qrcoderenders the value as a QR — qrErrorCorrection: 'L' | 'M' | 'Q' | 'H' barcodeEAN/UPC/Code128 — barcodeFormat progressderived percent rendered as a bar tagsfree-form tag array with autocomplete vectorembedding column — vectorConfig: { dimensions, distanceMetric: 'cosine' | 'euclidean', indexed, indexType: 'hnsw' | 'ivfflat' }
Field Type Notes idtext (ULID) primary key created_atdatetime UTC insert time updated_atdatetime UTC last-write time created_bylookup → user who inserted updated_bylookup → user who last wrote versioninteger optimistic-concurrency token
You don't declare these — opt out per object with
ObjectSpec.systemFields: false (rarely a good idea).
*.object.ts (field spec)
│
├─► Postgres / MySQL / SQLite column + index + constraint
├─► REST: validated on POST/PATCH, exposed on GET
├─► Console: form widget + list column
├─► AI Builder: tool argument schema (so the AI knows what to ask)
└─► Audit: change-tracked if `auditTrail: true`