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

# Usage

> Read your plan's allowances and how much of each you have used this cycle.

`GET /v1/usage` returns everything your account is entitled to and how much of it you have consumed in the current billing cycle — plan, cycle dates, and a meter per resource. Use it to show a usage widget, to decide whether to submit an FFmpeg job, or to check how many profile slots are left before you mint a connect link.

<Note>
  Publishing is unlimited on every paid plan (see [Posts](/concepts/posts)), so `uploads.limit` is `null` — the `used` counter still runs as a meter, not a cap.
</Note>

## Request

```bash theme={null}
curl https://api.madiad.com/v1/usage \
  -H "Authorization: Bearer $MADIAD_API_KEY"
```

The endpoint is scoped entirely to the key's own account — it takes no parameters and can never return another account's figures. It is a `GET`: it consumes no FFmpeg minutes and no uploads, only the per-minute [rate limit](/concepts/rate-limits).

## Response

```json theme={null}
{
  "plan": { "id": "growth", "name": "Growth", "price_vnd_monthly": 390000 },
  "status": "active",
  "period": { "start": "2026-07-07", "renews_on": "2026-08-07", "expires_on": null },
  "uploads": { "used": 180, "limit": null, "remaining": null },
  "ffmpeg_minutes": { "used": 12, "limit": 150, "remaining": 138 },
  "profiles": { "used": 4, "limit": 4, "remaining": 0 },
  "direct_messages": {
    "used": 0,
    "limit": 0,
    "remaining": 0,
    "day": "2026-07-20",
    "included": false
  },
  "api_keys": { "used": 2, "limit": null, "remaining": null },
  "features": { "schedule": true, "queue": true, "analytics": true, "webhooks": true }
}
```

### Meters

Every metered resource uses the same three fields:

| Field       | Meaning                                                                                         |
| ----------- | ----------------------------------------------------------------------------------------------- |
| `used`      | Consumed so far in the current cycle (for `direct_messages`, so far today).                     |
| `limit`     | The allowance. **`null` means unlimited.** `0` means the resource is not included in your plan. |
| `remaining` | `limit - used`, floored at 0. **`null` when `limit` is `null`.**                                |

<Warning>
  Treat `limit: null` as unlimited, not zero — a `remaining ?? 0` fallback will wrongly show your users as out of allowance.
</Warning>

### Fields

| Field               | Meaning                                                                                                                                                     |
| ------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `plan`              | The active plan's id, display name, and monthly price in VND (`null` for Custom).                                                                           |
| `status`            | Account status. Always `active` in this response: an `expired` or `banned` account is rejected with `403` before this endpoint runs (see the errors below). |
| `period.start`      | First day of the current cycle, `YYYY-MM-DD`.                                                                                                               |
| `period.renews_on`  | The day the cycle rolls over and the meters reset.                                                                                                          |
| `period.expires_on` | When the paid term ends, if one is set — otherwise `null`.                                                                                                  |
| `uploads`           | Posts published this cycle. `limit` is `null` on every paid plan.                                                                                           |
| `ffmpeg_minutes`    | [FFmpeg](/concepts/ffmpeg) minutes this cycle. The allowance is account-wide — all your brands draw from this one pool.                                     |
| `profiles`          | Connected [profiles](/concepts/profiles) against your plan's cap.                                                                                           |
| `direct_messages`   | Today's DM count. `included: false` means [engagement](/concepts/engagement) is not part of your plan.                                                      |
| `api_keys`          | Active (non-revoked) keys.                                                                                                                                  |
| `features`          | Feature flags for the active plan.                                                                                                                          |

## Cycle dates

Your cycle is anchored to the day your plan was activated, evaluated in Vietnam time (UTC+7) — **not** the first of the calendar month. A plan activated on the 7th resets on the 7th. An anchor day that does not exist in a shorter month is clamped to that month's last day.

`period.start` and `period.renews_on` always report the real dates, so read them rather than computing month boundaries yourself.

## Checking before you act

```bash theme={null}
# Only submit an FFmpeg job if minutes remain (null = unlimited).
REMAINING=$(curl -s https://api.madiad.com/v1/usage \
  -H "Authorization: Bearer $MADIAD_API_KEY" | jq '.ffmpeg_minutes.remaining')

if [ "$REMAINING" = "null" ] || [ "$REMAINING" -gt 0 ]; then
  echo "OK to submit"
fi
```

## Errors

| Status | Code           | Meaning                                                                                                            |
| ------ | -------------- | ------------------------------------------------------------------------------------------------------------------ |
| `401`  | `unauthorized` | Missing or invalid API key.                                                                                        |
| `403`  | `forbidden`    | The account is `expired` or `banned`. An expired account starts publishing again the moment a renewal is credited. |
| `429`  | `rate_limited` | Per-minute request rate limit exceeded.                                                                            |

See [Errors](/concepts/errors) for the full reference.
