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

# Bulk record action

> Registers a bulk action for records in Attio

<img className="dark:hidden" width="720" height="440" noZoom src="https://mintcdn.com/attio/4Fh2EPa8-SlLTNAV/images/bulk-record.png?fit=max&auto=format&n=4Fh2EPa8-SlLTNAV&q=85&s=fcf62f16279c33e94dd426e358cb3cb4" data-path="images/bulk-record.png" />

<img className="hidden dark:block" width="720" height="440" noZoom src="https://mintcdn.com/attio/4Fh2EPa8-SlLTNAV/images/bulk-record-dark.png?fit=max&auto=format&n=4Fh2EPa8-SlLTNAV&q=85&s=b8cb79ec596a9cdb91ce4d60e3ad42e6" data-path="images/bulk-record-dark.png" />

Bulk record actions are rendered when multiple record rows are selected in Attio.

Register a bulk record action by creating an `App.Record.BulkAction` and adding it to the
`record.bulkActions` array of your [`app.ts`](./app-ts) file.

## Example

```tsx send-invoices.ts theme={"system"}
import type {App} from "attio"

export const sendInvoicesAction: App.Record.BulkAction = {
  id: "send-invoices",
  label: "Send Invoices",
  icon: "Sales",
  onTrigger: async ({runRecordBatches}) => {
    // Run code here
  },
  objects: "people",
}
```

```tsx app.ts theme={"system"}
import type {App} from "attio"

import {sendInvoicesAction} from "./send-invoices"

export const app: App = {
  record: {
    bulkActions: [sendInvoicesAction],
    // ...
  },
  // ...
}
```

## Arguments

<ParamField path="id" type="string" required>
  The unique identifier for this action.

  It is only used internally; never shown to the user.
</ParamField>

<ParamField path="label" type="string" required>
  The human readable label for the record action.
</ParamField>

<ParamField path="icon" type="AttioIcon">
  An [`AttioIcon`](../icons) to display in the action.

  <Tip>
    If no `icon` prop is provided, it will default to your app's icon that you set up in the
    [Developer dashboard](https://build.attio.com).
  </Tip>
</ParamField>

<ParamField
  path="onTrigger"
  type={`async ({ runRecordBatches<TWorkerResult>(
options: RunRecordBatchesOptions,
worker: (batch: RecordBatch) => Promise<TWorkerResult>
): Promise<BulkRecordActionBatchRunOutcome<Exclude<TWorkerResult, void>>>,
object: ObjectSlug
}) => Promise<void>`}
>
  The function to run when the action is triggered. It receives an object with:

  * **`runRecordBatches`** — Processes the selected records in batches (up to 250 per batch).
    Call it with `options` (`batchSize`, and optional `onStart`, `onProgress`, `onComplete`, and
    `onError` lifecycle hooks) and a `worker` function that receives each `RecordBatch` and
    returns a promise. Returns a `BulkRecordActionBatchRunOutcome` with either `success: true` and
    `results`, or `success: false` with `partialResults` and `error`.
  * **`object`** — The [object slug](/docs/objects-and-lists) being processed (e.g.
    `"people"`, `"companies"`).

  You might run a [server function](../server/server-functions) inside the worker for each batch,
  and/or [show a dialog](../dialogs/show-dialog) or toast based on the outcome of
  `runRecordBatches`.
</ParamField>

<ParamField path="objects" type="ObjectSlug | Array<ObjectSlug>">
  A single slug or an array of slugs to select which types of record the record action will apply to.

  Defaults to `undefined`, which will cause the action to show on ***all*** types of records.

  The built-in slugs are

  * [`"companies"`](../../docs/standard-objects/standard-objects-companies)
  * [`"people"`](../../docs/standard-objects/standard-objects-people)
  * [`"deals"`](../../docs/standard-objects/standard-objects-deals)
  * [`"users"`](../../docs/standard-objects/standard-objects-users)
  * [`"workspaces"`](../../docs/standard-objects/standard-objects-workspaces)
</ParamField>
