Socotra
ConfigurationConfigurable UI (Beta)

Field Properties

Field properties set how a single field looks and behaves: its label, input control, format, help text, computed value, validation, visibility, and width. They are structured properties grouped by concern.

Set a field's baseline on the entity's data node, keyed by field name. Every page that renders the field uses it. For fields on the quote root, such as startTime, see Quote-Root Fields. This example is from uiConfigs/operationsWorkbench/products/HO3/config.json:

{
	"data": {
		"commission": {
			"display": { "label": "Commission", "format": "percentage" }
		},
		"expireIn": {
			"display": { "label": "Quote to expire in", "suffix": " days" },
			"tooltip": {
				"content": "Number of days after quote generation that the offer is valid for"
			}
		},
		"submissionDate": {
			"display": { "label": "Date Request Received" },
			"tooltip": {
				"content": "The date the request was received from the agent"
			}
		}
	}
}
PropertyTypeDescription
displayobjectHow the field renders and which input control it uses. See Display.
tooltipobjectHelp text shown on hover or focus. See Tooltip.
computeobjectDerives the field's value from another value plus an offset. See Compute.
validationobjectConstraints on the value. See Validation.
accessobjectWhether the field is visible and editable. See Field Access.
layoutobjectThe field's width and framing. See Field Layout.
prepopulatedbooleanPre-fills the field with a default or derived value on render.

The same properties apply to the fields of a custom data type, under the data type's own data node in dataTypes/. They apply wherever a field of that type is shown.

Quote-Root Fields

A quote or policy has a few fields on the entity root rather than inside data, such as startTime, endTime, and expirationTime. To relabel or reformat one everywhere it renders, add it as a top-level key on the product node, beside data and staticData. It takes the same properties as a data entry. This example is from uiConfigs/operationsWorkbench/products/HO3/config.json:

{
	"display": { "label": "Homeowners" },
	"startTime": {
		"display": { "label": "Proposed Effective Time", "format": "date" }
	},
	"expirationTime": { "display": { "label": "Expiration" } },
	"data": {
		"expireIn": { "display": { "label": "Quote to expire in" } }
	},
	"staticData": {
		"quoteDueDate": { "display": { "label": "Quote Due Date" } }
	}
}
  • A root field placed under data has no effect, because it isn't part of the product's data model.
  • A section's inline override for the same field wins over this one.
  • Only these root fields are recognized: startTime, endTime, expirationTime, effectiveTime, currency, timezone, billingLevel, billingTrigger, durationBasis, delinquencyPlanName, autoRenewalPlanName, and preferences.installmentPreferences.installmentPlanName. A misspelled field name is ignored.
  • Static data fields go under staticData, keyed by field name, in the same shape as data.

Display

PropertyTypeDescription
labelstring or objectThe field's label. A string is the label text; { "text": …, "markdown": true } renders it as markdown. Replaces the data model's displayName.
controlstring or objectThe input widget only: radio-group, dropdown, multiselect (with variant: "checkbox"), textarea, rich-text, table, or media. Omit to use the default for the data type.
formatstring or objectValue formatting: currency (optional currencyCode, defaulting to the quote currency), percentage, or date.
suggestionsarrayPre-written text options the user can insert: a string array, or groups gated by a condition, { "when": <condition>, "options": [...] }.
suffixstringStatic text after the input, such as " days".
detailsstringAdditional descriptive text for the field.
classNamestringA raw Tailwind CSS class. Use sparingly, and prefer a typed property when one exists.

Currency, percentage, and date are formats, not controls: set them in display.format, never in display.control.

The media control (file upload) takes multiple, minItems (the minimum when multiple is set), and scope: "quoteGroup" (attach documents to the quote group rather than the quote; the quote must already belong to a quote group). The rich-text control stores sanitized HTML, so formatting carries into generated documents.

Tooltip

Provide exactly one body source.

PropertyTypeDescription
contentstringInline tooltip text.
assetstringPath to a markdown file in the config assets.
formatstringmarkdown renders the body as markdown.

Compute

PropertyTypeDescription
fromstringThe base value: a field path, bare for a quote-root field (startTime) and data.-prefixed for a data field (data.expireIn), or a token (today, submissionDate).
opstringadd or subtract.
amountnumberA literal offset. Mutually exclusive with amountField.
amountFieldstringReads the offset from another field, such as data.expireIn. Mutually exclusive with amount.
unitstringdays or years.

This example sets a date one year after the start date:

{
	"compute": { "from": "startTime", "op": "add", "amount": 1, "unit": "years" }
}

Validation

PropertyTypeDescription
min, maxnumber, compute object, or { field }A literal bound, a relative bound (such as today plus 180 days), or a bound taken from another field.
stepnumberThe value must be a multiple of this step, such as 1000.

Field Access

A field takes the data-driven subset of access:

EffectFormDescription
readfalseAlways hide the field.
read{ "unless": <condition> }Hide the field while the condition holds.
writefalseShow the value but block editing.

Omit an effect to leave it granted. Keep the following in mind:

  • read is the only field effect that takes a condition. A field's write is unconditional; to make fields read-only under a condition, set access.write on the section or step instead.
  • A field can't use roles, scope, when, or a list of alternative rules. Put those on the section or step instead; they cascade to the fields inside.
  • A field's unless must be flat: a single condition, or one all or any group.
  • For a field whose value is an array, such as a multi-select, eq and in mean "contains". Prefer scalar fields for field conditions.

In this example, from a product's data, the producer code is hidden unless isThisCannedPlan is "Yes", and can't be edited:

{
	"producerCode": {
		"access": {
			"read": {
				"unless": {
					"field": "isThisCannedPlan",
					"operator": "neq",
					"value": "Yes"
				}
			},
			"write": false
		}
	}
}

Field Layout

A field accepts a subset of the layout object.

AxisField valuesDescription
widthfull, 1/2The field's width in its row. Omit for the default grid cell.
variantflatComplex fields only. Drops the field's frame.
collapseexpandedOn a complex field, renders the field in a collapsible panel, open by default. On a primitive field, adds an add/remove toggle instead. See the warning below.
orientationhorizontalComplex fields only. Controls how the field's nested children flow. [TODO: confirm wording with engineering; the guide describes horizontal as stacking children one per row.]

On a primitive field, collapse is destructive: collapsing the field clears its value. Set it on a primitive field only where that is intended.

Baseline and Inline Overrides

When a section lists a field in include, the entry can be a bare path or an inline override: an object with the field's path in fieldName, plus any field properties. For example, in a section:

{
	"include": [
		{
			"fieldName": "startTime",
			"display": { "label": "Effective Date", "format": "date" }
		},
		"data.submissionDate"
	]
}

An inline override applies only to the section that declares it, and wins over the baseline for the properties it sets. Use the baseline for presentation that should apply everywhere, and inline overrides for one-off wording or behavior.

In the editor, an inline override can't set access yet. Set it on the field's baseline or on the section instead.

Next Steps

See Also

On this page