# Customs Trade Statistics API

Ranks and value shares of customs trade aggregated by HS code, origin country, destination country, or time period. Covers customs filings and trade statistics from about 95 countries, including the United States, Mexico, Brazil, Colombia, India, Indonesia, Vietnam, Pakistan, Russia, Turkey, the UK and the EU.

**Pricing:** $0.035 per aggregate bucket

**Endpoint:** `POST /v1/data/customs/trade-stats/run`

**Auth:** `Authorization: Bearer mk_live_...`

## Parameters

| Parameter | Type | Required | Description |
|-----------|------|----------|-------------|
| `groupBy` | string | No | How to bucket matching trade records: by HS code, origin country, destination country, or time period. |
| `direction` | string | No | Whether to aggregate import records or export records. |
| `product` | array | No | Product description keywords to match; one of product, HS code, importer or exporter is required. |
| `hsCode` | string | No | A customs HS code of 4 or more digits (a 2-digit chapter code needs another filter alongside it). |
| `importer` | string | No | An importing company name to filter records by. |
| `exporter` | string | No | An exporting company name to filter records by. |
| `originCountry` | array | No | Restrict to these origin countries, as ISO 3166 alpha-3 codes (e.g. COL, USA). Pick from the list; English country names are also accepted. |
| `destinationCountry` | array | No | Restrict to these destination countries, as ISO 3166 alpha-3 codes (e.g. COL, USA). Pick from the list; English country names are also accepted. |
| `startDate` | date | No | Start of the query window, defaults to one year before the end date. |
| `endDate` | date | No | End of the query window, defaults to today. |
| `periodUnit` | string | No | Bucket size used only when grouping by time period. |
| `maxResults` | integer | No | How many aggregate buckets to return in total. Defaults to 100; use 0 for all. |

## Example

`?wait=true` holds the request open until the run finishes (up to 60s) and returns the rows inline: one request, no polling.

```bash
curl -X POST "https://api.mindcase.co/v1/data/customs/trade-stats/run?wait=true" \
  -H "Authorization: Bearer mk_live_YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"params":{}}'
```

```python
import requests

resp = requests.post(
    "https://api.mindcase.co/v1/data/customs/trade-stats/run",
    params={"wait": "true"},
    headers={"Authorization": "Bearer mk_live_YOUR_API_KEY"},
    json={"params": {}},
)
rows = resp.json()["data"]
```

## Longer runs

If the run is still going at the 60s ceiling you get back `{ job_id, status: "running" }` instead of rows (same if the result is over 100 rows; those come back `truncated`). Poll with that `job_id`:

```bash
# 1) check status
curl https://api.mindcase.co/v1/jobs/JOB_ID \
  -H "Authorization: Bearer mk_live_YOUR_API_KEY"

# 2) when status == completed, fetch the rows
curl https://api.mindcase.co/v1/jobs/JOB_ID/results \
  -H "Authorization: Bearer mk_live_YOUR_API_KEY"
```

Full API reference (auth, jobs, balance, SDKs, MCP): https://mindcase.co/skills.md

## Response columns

| Field | Display name | Type |
|-------|--------------|------|
| `bucketKey` | Bucket Key | text |
| `groupBy` | Grouped By | text |
| `descriptionEn` | Description | text |
| `countryCode` | Country Code | text |
| `countryName` | Country Name | text |
| `period` | Period | text |
| `weightKg` | Weight (kg) | number |
| `quantity` | Quantity | number |
| `valueUsd` | Reported Value (USD) | currency |
| `unitPricePerKgUsd` | Unit Price per kg (USD) | currency |
| `unitPriceUsd` | Unit Price (USD) | currency |
| `tradeCount` | Trade Count | integer |
| `valueSharePct` | Value Share (%) | percentage |
