---
title: setAttributes
description: Attach string metadata to workflow run for observability.
type: reference
summary: Use setAttributes inside a workflow or step function to set run attributes.
prerequisites:
  - /docs/foundations/workflows-and-steps
related:
  - /docs/observability/attributes
  - /docs/api-reference/workflow/fatal-error
---

# setAttributes



Attaches string metadata to the current workflow run.

```typescript lineNumbers
import { setAttributes } from "workflow"

export async function orderWorkflow(orderId: string) {
  "use workflow"

  await setAttributes({
    phase: "received",
    orderId,
  })
}
```

## API signature

### Parameters

<TSDoc
  definition={`
import { setAttributes } from "workflow";
export default setAttributes;`}
  showSections={['parameters']}
/>

## Usage

Call `setAttributes` from a `"use workflow"` function or a `"use step"` function. Calling it from plain application code is not supported because there is no active workflow run.

Attribute values must be strings. Pass `undefined` to remove an attribute:

```typescript lineNumbers
import { setAttributes } from "workflow"

export async function cleanupAttributes() {
  "use workflow"

  await setAttributes({ staleKey: undefined })
}
```

Attribute keys must be 1-256 characters, values must be strings up to 256 bytes, and each run can have up to 64 attributes. Keys that start with `$` are reserved for framework and library code.

Each call's complete `attr_set` event data must also fit in **8192 UTF-8 JSON bytes (8KiB)**. This includes the change keys and values, JSON escaping and structure, writer metadata (including the step ID and attempt for step calls), and the reserved-key option when enabled. It is not a limit on values alone. Split large updates into smaller calls; updates across multiple calls are not atomic and still share the 64-attribute per-run limit.

Validation errors reject `setAttributes` with [`FatalError`](/docs/api-reference/workflow/fatal-error) before a new attribute write is attempted. Catch the error if the metadata is best-effort; an uncaught error fails the workflow or step. Previously persisted attribute events remain replayable.

Calls from both workflow and step bodies append a native `attr_set` event, which the World materializes onto `run.attributes`. Workflow-originated events record a workflow writer; step-originated events record the originating step ID and attempt.

Native attributes require spec version 4 or later. Step-body storage errors throw from `setAttributes`; catch them inside the step if the write should be best-effort. Workflow-body writes are committed when the workflow suspends: transient storage errors are retried with the suspension, while a write the World rejects as invalid (such as exceeding the per-run attribute cap across multiple calls) fails the run with the validation error.


---

For a semantic overview of all documentation, see [/sitemap.md](/sitemap.md)

For an index of all available documentation, see [/llms.txt](/llms.txt)

For agent-facing discovery, including API and MCP surfaces, see [/agents.md](/agents.md)