Bindable Field

Toggles between a value picker (a Select / MultiSelect) and a variable expression text field. It always renders a bind/unbind toggle button automatically, so you don't need to manage that yourself.

 

Installation

import { BindableField } from "@octopusdeploy/design-system-octopus-components"

BindableField lets a user either pick a value from a Select / MultiSelect or a TextField where you can bind the field to an Octopus variable by typing, or inserting a variable (e.g. #{Octopus.Environment.Name}) via the InsertVariableActions dropdown. A single toggle switches between the two mode. The toggle is generated automatically and always sits last in the action row.

Mode

Editor rendered

Toggle shown

Purpose

Unbound (default)

Select (default) or
MultiSelect when multiple is set

Bind to variable (link icon)

Pick a value from a list

Bound

TextField

Unbind (broken-link icon)

Type/insert a #{Variable} expression

The two modes hold independent values the selection and the variable expression are separate state the consumer owns. Toggling will not move data between them.

Actions

Actions are declarative shapes that BindableField resolves and wires up for you, or a custom icon-only Button that you can customise yourself.

How they work

We allow two action slots per form field the toggle for Bind/Unbind claims one.

  • Toggle Action: BindableField appends the bind/unbind toggle itself so each editor shows an action followed by the toggle (two buttons total).
  • Second Action: InsertVariableAction is only valid as a boundAction. Whereas addEntity and custom buttons work in either mode.
  • In bound mode the field also shows a clear (✕) control that resets the field value - this is separate from your action.
  • The refresh button is not counted as one of the actions and is handled separately with its own dedicated slot. The long term plan is to move it into the Select/Multiselect.

Action shapes

Shape

Ownership

Available in

Behaviour

insertVariable

Prebuilt
The button, dropdown, and caret insertion are all handled; you supply the variable list.

Bound only (boundAction)

Opens a dropdown of variables and inserts the chosen one as #{value} at the caret.

addEntity

Mixed
The button is prebuilt; you own the onClick behaviour and whatever it opens.

Both

A generic "+" button; the consumer owns whatever it opens.

Raw Button

Consumer
You build and manage the whole button.

Both

A bespoke icon-only action you manage yourself.

refresh

Prebuilt
Button, spinner, and screen-reader announcement handled; you supply the refresh function.

Select mode only (via AsyncList.refresh)

Auto-rendered when the items AsyncList defines refresh. Reloads the list. Not configured through the action props.

Does not count as one of your action slots.

Insert Variable Action

An icon-only action button that opens a dropdown of Octopus variables and inserts the selected one (#{VariableName}) into a text field's value.

Refresh (automatic, select mode)

The refresh button is not configured through selectAction / boundAction. It is provided by the data source: when items is an AsyncList whose refresh function is defined, the unbound Select / MultiSelect automatically renders a refresh button.

  • Select mode only: It appears alongside the select input.
  • Driven by data, not props: Pass an AsyncList with a refresh method to get it; omit refresh and no button renders.
  • It's additional to your one custom action: Refresh doesn't count as a selectAction slot, so an async list can show refresh and your addEntity action and the bind toggle at the same time.
  • Async feedback: If refresh returns a promise, the arrow spins until it settles and the outcome is announced to screen readers.

Disabled/ReadOnly States

BindableField treats every action button it renders as an edit affordance. Inserting a variable mutates the value, adding an entity feeds the selection, and the bind/unbind toggle switches editors. Setting either disabled or readOnly therefore disables all of the actions, not just the input.

What each state does

 

disabled

readOnly

Select / MultiSelect Field (unbound mode)

Dropdown won't open

Dropdown won't open

TextField (bound mode)

Not editable

Focusable but not editable

Bind / unbind toggle

Disabled

Disabled

InsertVariableAction

Disabled

Disabled

addEntity Action

Disabled

Disabled

Refresh button (async lists)

Disabled

Disabled

Declarative actions vs custom elements

Declarative action shapes e.g. addEntity and InsertVariable are automatically disabled for you this will override A per-any field state.

If you pass a raw icon-only Button element as selectAction or boundAction, it will be rendered exactly as supplied disabling it in the disabled/readonly states is your responsibility which you can set on the button itself.