---
title: "List API request logs"
method: GET
path: "/v1/developers/request-logs"
tags: ["RequestLogs"]
deprecated: true
---

# List API request logs

`GET /v1/developers/request-logs`

## Request

- Base URL: `https://app.beel.es/api`
- URL: `https://app.beel.es/api/v1/developers/request-logs`
- Auth: HTTP bearer

> **Deprecated.**

Returns the history of public API requests made by you, with any of your API keys in this
environment — not only the key you are authenticating with. Only `auth_type=API_KEY`
traffic is recorded.

- **Deprecated:** use `GET /v1/accounts/{account_id}/request-logs`, whose result set is
  identical.

## Whose traffic you see

- **The axis is the person, not the individual credential:** a second key of yours sees the
  same history, and narrowing it to one key is a filter (`api_key_id`), not the default.
  Requests made by other users, including other users of the same account, are never
  returned.
- **Environment is not a filter:** results are always scoped to the environment of the
  credential you authenticate with — a `beel_sk_test_*` key sees the test traffic of all
  your test keys, a `beel_sk_live_*` key the live traffic of all your live ones. To see
  the other environment, use a key from that environment.

## Browsing the history

- **Cursor pagination:** navigate with the opaque `cursor` returned in `next_cursor` /
  `prev_cursor`; there is no jump to an arbitrary page N.
- **Time window:** defaults to the last 30 days; narrow or move it with `from`/`to`.

**Retires on 9 December 2026.** See the [migration guide](https://docs.beel.es/changelog/resources-under-the-nif) for what moved where and what changes when you switch.

## Query parameters

- `only_errors` boolean
- `method` string
- `http_status` integer
- `path_contains` string
- `api_key_id` string, uuid
- `from` string, date-time
- `to` string, date-time
- `cursor` string
- `limit` integer

## Response `200`

Logs retrieved successfully.

- RequestLogListResponse
  - `success` boolean, required
  - `data` object, required
    - `request_logs` RequestLogSummary[], required
      - `request_id` string, required: Request correlation identifier (X-Request-Id header).
      - `timestamp` string, date-time, required: Time the request was received.
      - `http_method` string, required
      - `http_path` string, required
      - `http_status` integer, required
      - `duration_ms` integer, nullable: Request latency in milliseconds.
      - `environment` 'TEST' | 'PROD': Mode a record lives in — its Test/Live twin. It decides where invoices, customers and quota are accounted. For a company it also decides which AEAT its NIF is registered against: switching a company on in `PROD` is what registers it with the real AEAT, so `aeat_environment` is that same mode and uses this same enum.
      - `api_key_id` string, uuid, nullable: Id of the API key the request authenticated with.
      - `error_code` string, nullable: Public error code returned (e.g. INVOICE_NOT_FOUND). Null if the request succeeded.
      - `client_ip` string, nullable
    - `pagination` RequestLogCursorPagination: Cursor-based pagination (keyset on _time + request_id). APL does not support cheap offset.
      - `next_cursor` string, nullable: Opaque cursor for the next (older) page. Null if there are no more.
      - `prev_cursor` string, nullable: Opaque cursor for the previous (newer) page. Null if this is the first.
      - `has_next` boolean, required
      - `has_previous` boolean, required
  - `meta` ResponseMeta
    - `timestamp` string, date-time
    - `request_id` string

## Other responses

- `400`: Bad request. From a dashboard session, a `BeeL-Environment` header whose value is not a known environment answers `ENVIRONMENT_HEADER_INVALID`, with the header named in `error.details` (`{"BeeL-Environment": "invalid"}`); it is never read as production. `BUSINESS_RULE_VIOLATION` is the generic answer to an operation the resource does not admit in its current state when that state has no code of its own. It carries no `details`; read the resource again before retrying.
- `401`: Missing or invalid authentication. Like every other error, `message`/`detail` is localized according to `Accept-Language` (`es`, `en`, `ca`); defaults to English when the header is missing or asks for none of those.
- `403`: Authenticated but not allowed. Fourteen causes shared by every operation, told apart by `error.code`; an operation that adds a cause of its own names it in its `403`. You can branch on them exhaustively. - `INSUFFICIENT_SCOPE` — the credential lacks a scope the operation requires; `error.details.missing_scopes` names them as a single comma-separated string (for example `"invoices:write,customers:read"`), not as an array; `required_scopes` has the same shape and lists every scope the operation needs. Retrying will not help: mint a key that holds them. - `COMPANY_READ_ONLY` — the scope is there, but your access level over that NIF only lets you read it. - `ACCOUNT_MANAGEMENT_FORBIDDEN` — the scope is there, but your role over the account, or the management relationship you hold over it, does not cover this operation. - `ACCOUNT_NOT_ACCESSIBLE` — the account is not yours to reach, which is also the answer when it does not exist, so existence is never disclosed. - `ACTIVE_COMPANY_NOT_ACCESSIBLE` — the same, for a NIF: the company in the path, or the one named by `BeeL-Active-Company`, is not one this credential may reach — and again, this is also the answer when it does not exist. - `COMPANY_ACCESS_REVOKED` — your access to the NIF was withdrawn while the request was already in flight, so the write was rejected and nothing was recorded. Retrying will not help until the access is granted again. - `LIVE_CREDENTIAL_REQUIRED` — the operation changes the real account and the call came from a test API key (`beel_sk_test_…`). Use your live key or the dashboard. - `FEATURE_NOT_AVAILABLE` — your subscription does not include the entitlement the operation needs; `error.details.feature_code` names it. This gate runs **before** the scope gate, so for such an operation you never see `INSUFFICIENT_SCOPE` first. - `NO_ACTIVE_ACCOUNT` — the credential does not resolve to an account, so no scope can be evaluated against one. Fail-closed, not a permission that can be granted to you. - `OPERATION_REQUIRES_SESSION` — the operation is available only from the web session; no API key and no OAuth2 token can perform it, whatever scopes it holds. - `OPERATION_REQUIRES_API_KEY` — the reverse: the operation needs a scope that only an API key can hold (such as `accounts:write`), so a dashboard session never satisfies it. - `API_KEY_LIVE_NOT_AVAILABLE` — the call came with a live API key (`beel_sk_live_…`) and the account has no Live mode yet. It is never degraded to Test: use your test key, or activate Live first. - `ACCOUNT_REQUIRES_FOCUS_SWITCH` — dashboard session only: you are a member of the account in the path, but it is not the account in focus. Switch focus to it and retry. - `REQUEST_BLOCKED` — the edge security filter stopped the request before the API saw its body, usually because a text field carries something that looks like markup or a script (HTML tags, `<script>`). Review the body and retry.
- `422`: The query was understood and refused. `error.code` is `REQUEST_LOG_INVALID_CURSOR` when `cursor` is not a cursor this API issued, `REQUEST_LOG_INVALID_TIME_RANGE` when `from` is later than `to` (with either one defaulted: `to` is now and `from` a window before `to`), or `VALIDATION_ERROR` when another query parameter falls outside its declared range. Send the `cursor` exactly as returned by the previous page; a hand-built or truncated value is never accepted.
- `500`: Internal server error
- `default`: Any status code the operation does not list above. Every operation declares it, so a generated client always has a branch to fall into and never loses the cause of a failure it did not anticipate. This is where the transport-level answers land — `405`, `406`, `415` and `429` — together with any status a future version of the API starts returning. All of them carry the same error envelope as the codes listed explicitly, so `error.code` is what tells them apart: switching on the status code alone is not enough. See «Transport-level errors» in the API description for when each one is produced. A `402` carrying `SUBSCRIPTION_REQUIRED` lands here when the account has no active subscription. `error.details` says why and what to do: `current_status` (absent if it never had one), `required_permission` and `action`. A `503` carrying `SERVICE_UNAVAILABLE` lands here too, with a `Retry-After` header: a dependency of BeeL itself (the database, the email provider) was momentarily unavailable and nothing was done. Retry after those seconds. A `502` carrying `EXTERNAL_SERVICE_ERROR` also lands here: an outbound integration the operation depends on failed or did not answer in time. It is a transient condition — retry with the same `Idempotency-Key` where the operation accepts one. One exception to the envelope: a failure of the network edge that never reaches the application (`502`, `503`, `504`, `524`) is generated by Cloudflare and its body is not BeeL's — it may not even be JSON. Treat those as "no answer", and retry.

---

[API](https://skmtc.dev/beel/apis/beel-public-api.md) · [All operations](https://skmtc.dev/beel/apis/beel-public-api/llms.txt) · [OpenAPI document](https://skmtc.dev/beel/apis/beel-public-api/revisions/ffbc0ae31f79?raw)
