> ## Documentation Index
> Fetch the complete documentation index at: https://docs.cyberdesk.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Empty Values

> Handle optional form fields in workflows with the __EMPTY__ sentinel value

When developers want to skip certain form fields in workflows, Cyberdesk provides the `__EMPTY__` sentinel value.

If you want to actively clear an already-filled field instead, use [`__CLEAR__`](/concepts/clear-values).

Cyberdesk also treats optional empty strings and `null` values as "not provided" when building run inputs, so they are normalized to `__EMPTY__` before execution.

## Simple Use Case

**Problem**: Sometimes workflows have optional form fields that should be skipped when no data is provided.

**Solution**: Use `__EMPTY__` to skip typing while maintaining workflow structure.

## Example

```python theme={null}
# User provides username but no email
input_values = {"username": "john_doe", "email": "__EMPTY__"}

# Agent behavior:
type_text("john_doe")  # Types the username
type_text("__EMPTY__")  # Skips typing (no email provided)
```

## Automatic `__EMPTY__` for Missing Nested Fields

When using [structured inputs](/concepts/structured-inputs) with nested access, missing fields automatically become `__EMPTY__`:

```python theme={null}
# Prompt uses: {patient.middle_name}
# Input only has first and last name:
input_values = {
    "patient": {
        "first_name": "John",
        "last_name": "Doe"
        # middle_name is not provided
    }
}

# Result: {patient.middle_name} → __EMPTY__
```

This allows workflows to gracefully handle optional nested fields without requiring explicit `__EMPTY__` values.

## Nested Access on `__EMPTY__` Values

If a root variable is `__EMPTY__` and you try to access a nested property on it, the result is also `__EMPTY__`:

```python theme={null}
# Prompt uses: {extra_info.notes}
# User provides nothing for extra_info (auto-converted to __EMPTY__)
input_values = {"extra_info": "__EMPTY__"}

# Result: {extra_info.notes} → __EMPTY__
```

This allows workflows to gracefully skip entire optional sections without failing.

<Note>
  **Type errors are different**: If you try to access a nested property on a value that is a concrete type like a string or number (e.g., `{patient.name.first}` when `patient.name` is `"John Doe"`), the run fails immediately with a clear error. Only missing fields and `__EMPTY__` values become `__EMPTY__`.
</Note>

## Input Schema Validation

When a workflow has an input schema, `__EMPTY__` is treated as "not provided" for validation.

* Object fields set to `__EMPTY__` are ignored during schema validation.
* Array entries set to `__EMPTY__` are removed before validation.
* This applies to auto-generated `__EMPTY__` values too, including optional inputs left blank as empty strings or `null`.

This lets optional fields stay blank without failing validation, while required fields still need a real value unless your schema allows them to be omitted.

## When to Use

* **Optional form fields** that might not always be filled
* **Progressive workflows** where some data is provided later
* **A/B testing** different workflow variants
* **Graceful degradation** when inputs are missing
* **Nested optional fields** in structured input objects

## Best Practice

```python theme={null}
# ✅ Good: Simple optional step
type_text("__EMPTY__", conditional="input_values['optional_field'] == '__EMPTY__'")

# ❌ Avoid: Complex logic - split workflows instead
```

This is a simple convenience feature for handling occasional missing data - not for complex workflow logic.

If you need to blank out an existing value instead of skipping, see [Clear Values](/concepts/clear-values).
