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

# Get Automation Activity

> Cursor-paginated audit log for one automation

export const PlansAvailable = ({plans = [], maxPackRequired}) => {
  let displayPlans = plans;
  if (plans && plans.length === 1) {
    const lowerCasePlan = plans[0].toLowerCase();
    if (lowerCasePlan === "business") {
      displayPlans = ["Launch", "Business", "Enterprise"];
    } else if (lowerCasePlan === "premium") {
      displayPlans = ["Premium", "Launch", "Business", "Enterprise"];
    }
  }
  return <Note>
Available on {displayPlans.length === 1 ? "the " : ""}
{displayPlans.join(", ").replace(/\b\w/g, l => l.toUpperCase())}{" "}
{displayPlans.length > 1 ? "plans" : "plan"}.

{maxPackRequired && <span onClick={() => window.open('https://www.ayrshare.com/docs/additional/maxpack', '_self')} className="flex items-center mt-2 cursor-pointer">
 <span className="px-1.5 py-0.5 rounded text-sm" style={{
    backgroundColor: '#C264B6',
    color: 'white',
    fontSize: '12px'
  }}>
   Max Pack required
 </span>
</span>}
</Note>;
};

export const HeaderAPI = ({noProfileKey, profileKeyRequired}) => <>
    <ParamField header="Authorization" type="string" required>
      <a href="/apis/overview#authorization">API Key</a> of the Primary Profile.
      <br />
      <br />
      Format: <code>Authorization: Bearer API_KEY</code>
    </ParamField>
    {!noProfileKey && (profileKeyRequired ? <ParamField header="Profile-Key" type="string" required>
          <a href="/apis/overview#profile-key-format">Profile Key</a> of a User Profile.
          <br />
          <br />
          Format: <code>Profile-Key: PROFILE_KEY</code>
        </ParamField> : <ParamField header="Profile-Key" type="string">
          <a href="/apis/overview#profile-key-format">Profile Key</a> of a User Profile.
          <br />
          <br />
          Format: <code>Profile-Key: PROFILE_KEY</code>
        </ParamField>)}
  </>;

<PlansAvailable plans={["business", "enterprise"]} maxPackRequired={false} />

<Note>
  **Beta.** See the [Automations Overview](/apis/automations/overview) for the full feature description.
</Note>

Returns every dispatch attempt for one automation, newest first. Each row records the recipient, the matched trigger, every action's result, and any error.

Rows from the last **30 days** are returned. Older rows exist in Firestore (retention is indefinite for analytics) but are excluded from this endpoint for performance.

## Activity row status

Each row has a top-level `status` plus a per-action `status` inside `actionResults[]`.

| Status         | When it's recorded                                                                                            |
| -------------- | ------------------------------------------------------------------------------------------------------------- |
| `pending`      | Row was just written; the worker hasn't picked it up yet                                                      |
| `in_flight`    | The worker is currently dispatching                                                                           |
| `sent`         | Every action succeeded                                                                                        |
| `failed`       | At least one action failed (and none hit an auth error)                                                       |
| `auth_error`   | The Instagram access token was invalid; the DM was not retried                                                |
| `rate_limited` | The daily DM cap (tier or per-profile) was hit. No DM was sent                                                |
| `deduplicated` | This action already fired to this recipient inside its dedup window (default 7 days, per-action configurable) |
| `skipped`      | The automation became inactive or was deleted between fan-out and dispatch                                    |

`pending` and `in_flight` are transient; everything else is terminal.

## Header Parameters

<HeaderAPI noProfileKey={false} />

## Path Parameters

<ParamField path="id" type="string" required>
  The automation ID returned from `POST /automations`.
</ParamField>

## Query Parameters

<ParamField query="limit" type="number" default={25}>
  Page size. Default `25`, max `100`. Values outside `[1, 100]` are clamped; non-integer or `≤0` returns HTTP 400.
</ParamField>

<ParamField query="next" type="string">
  Opaque cursor from a previous response's `meta.pagination.next`. Omit on the first request.

  Forward-only — passing `?previous=` returns HTTP 400.
</ParamField>

## Response Shape

The response wraps the result list in `activity[]` and the cursor info in `meta.pagination`:

```json theme={"system"}
{
  "status": "success",
  "automationId": "auto_9xKp2Lm4nQ",
  "activity": [ /* …rows, newest first… */ ],
  "meta": {
    "pagination": {
      "hasMore": true,
      "limit": 25,
      "next": "eyJ0aW1lIjoiMjAyNi0wNS0xMlQwOTowMDoxMS4wMDBaIiwiaWQiOiJhdXRvXzl4S3AyTG00blE6dHJnX2ExYjJjMzpjb21tZW50X3JlY2VpdmVkOjE4MDEyMzQ1Njc4OTAwMDAwIn0="
    }
  }
}
```

`meta.pagination.next` is a base64-encoded opaque blob — treat it as a black box and pass it back unchanged in the next request's `?next=`. `meta.pagination.hasMore` is `true` when at least one more page exists.

<RequestExample>
  ```bash cURL — first page theme={"system"}
  curl \
  -H "Authorization: Bearer API_KEY" \
  -X GET "https://api.ayrshare.com/api/automations/auto_9xKp2Lm4nQ/activity?limit=25"
  ```

  ```bash cURL — next page theme={"system"}
  curl \
  -H "Authorization: Bearer API_KEY" \
  -X GET "https://api.ayrshare.com/api/automations/auto_9xKp2Lm4nQ/activity?limit=25&next=eyJ0aW1lIjoiMjAyNi0wNS0xMlQw..."
  ```

  ```javascript JavaScript theme={"system"}
  const API_KEY = "API_KEY";
  const id = "auto_9xKp2Lm4nQ";

  // Paginate through every page
  let next;
  do {
    const url = new URL(`https://api.ayrshare.com/api/automations/${id}/activity`);
    url.searchParams.set("limit", "25");
    if (next) url.searchParams.set("next", next);

    const res = await fetch(url, {
      headers: { "Authorization": `Bearer ${API_KEY}` },
    });
    const json = await res.json();
    console.log(json.activity);
    next = json.meta?.pagination?.hasMore ? json.meta.pagination.next : undefined;
  } while (next);
  ```

  ```python Python theme={"system"}
  import requests

  headers = {"Authorization": "Bearer API_KEY"}
  automation_id = "auto_9xKp2Lm4nQ"

  params = {"limit": 25}
  while True:
      r = requests.get(
          f"https://api.ayrshare.com/api/automations/{automation_id}/activity",
          params=params,
          headers=headers,
      ).json()
      print(r["activity"])
      pagination = r.get("meta", {}).get("pagination", {})
      if not pagination.get("hasMore"):
          break
      params["next"] = pagination["next"]
  ```

  ```php PHP theme={"system"}
  $id = "auto_9xKp2Lm4nQ";
  $curl = curl_init();

  curl_setopt_array($curl, [
      CURLOPT_URL => "https://api.ayrshare.com/api/automations/" . $id . "/activity?limit=25",
      CURLOPT_RETURNTRANSFER => true,
      CURLOPT_CUSTOMREQUEST => "GET",
      CURLOPT_HTTPHEADER => ["Authorization: Bearer API_KEY"],
  ]);

  $response = curl_exec($curl);
  curl_close($curl);
  echo $response;
  ```
</RequestExample>

<ResponseExample>
  ```json 200: Success theme={"system"}
  {
    "status": "success",
    "automationId": "auto_9xKp2Lm4nQ",
    "activity": [
      {
        "id": "auto_9xKp2Lm4nQ:trg_a1b2c3:18012345678901234",
        "automationId": "auto_9xKp2Lm4nQ",
        "triggerId": "trg_a1b2c3",
        "triggerType": "comment_keyword",
        "recipientId": "17841401234567890",
        "recipientUsername": "jane_doe",
        "eventId": "18012345678901234",
        "platform": "instagram",
        "status": "sent",
        "actionResults": [
          {
            "actionId": "act_d4e5f6",
            "type": "send_dm",
            "status": "sent",
            "completedAt": "2026-05-12T09:14:48.000Z"
          }
        ],
        "keyword": "LINK",
        "commentText": "Send me the LINK please!",
        "created": "2026-05-12T09:14:22.000Z",
        "completedAt": "2026-05-12T09:14:48.000Z"
      },
      {
        "id": "auto_9xKp2Lm4nQ:trg_a1b2c3:18012345678900000",
        "automationId": "auto_9xKp2Lm4nQ",
        "triggerId": "trg_a1b2c3",
        "triggerType": "comment_keyword",
        "recipientId": "17841409876543210",
        "recipientUsername": "repeat_user",
        "eventId": "18012345678900000",
        "platform": "instagram",
        "status": "deduplicated",
        "actionResults": [],
        "keyword": "LINK",
        "commentText": "LINK again please",
        "created": "2026-05-12T09:00:11.000Z",
        "completedAt": "2026-05-12T09:00:34.000Z"
      }
    ],
    "meta": {
      "pagination": {
        "hasMore": true,
        "limit": 25,
        "next": "eyJ0aW1lIjoiMjAyNi0wNS0xMlQwOTowMDoxMS4wMDBaIiwiaWQiOiJhdXRvXzl4S3AyTG00blE6dHJnX2ExYjJjMzoxODAxMjM0NTY3ODkwMDAwMCJ9"
      }
    }
  }
  ```

  ```json 400: Bad limit theme={"system"}
  {
    "status": "error",
    "message": "limit must be a positive integer"
  }
  ```

  ```json 400: Backward pagination not supported theme={"system"}
  {
    "status": "error",
    "message": "'previous' pagination is not supported by this endpoint"
  }
  ```

  ```json 404: Not found theme={"system"}
  {
    "action": "automation",
    "status": "error",
    "code": 469,
    "message": "Automation not found"
  }
  ```
</ResponseExample>
