Every response from the NGN Market API follows the same JSON structure whether the request succeeds or fails. This means you can write one response-handling layer in your application and rely on the same fields being present for every endpoint.
Successful response
{
"success": true,
"data": { },
"meta": {
"plan": "starter",
"calls_used": 4821,
"calls_remaining": 95179,
"reset_at": "2026-05-01T00:00:00.000Z"
}
}
Top-level fields
| Field | Type | Description |
|---|
success | boolean | true on success, false on error |
data | object | array | The endpoint payload. Shape varies — see individual endpoint pages. |
meta | object | Quota state for your account. Present on every successful authenticated response. |
| Field | Type | Description |
|---|
plan | string | Your current plan: free, starter, growth, business, or enterprise |
calls_used | integer | Total calls made this calendar month across all your keys |
calls_remaining | integer | Calls left before your quota is exhausted |
reset_at | string | ISO 8601 UTC timestamp — always the 1st of next month at midnight |
Check meta.calls_remaining in your app so you can detect when you are close to your limit before hitting it.
Error response
When a request fails, success is false and the response includes an error object instead of data.
{
"success": false,
"error": {
"code": "PLAN_REQUIRED",
"message": "This endpoint requires a starter plan or higher.",
"required_plan": "starter",
"current_plan": "free"
}
}
Error object fields
| Field | Type | Description |
|---|
code | string | Machine-readable error identifier. Use this to branch error handling in your code. |
message | string | Human-readable description of what went wrong. |
required_plan | string | (PLAN_REQUIRED only) Minimum plan needed to access this endpoint. |
current_plan | string | (PLAN_REQUIRED only) Your account’s current plan. |
The QUOTA_EXCEEDED error (429) includes both an error object and a meta object so you can still read your quota state when you are over the limit. See Rate limits for the full example.
Handling responses in code
Check success first, then branch on error.code for specific handling:
const res = await fetch('https://api.ngnmarket.com/v1/market/snapshot', {
headers: { Authorization: 'Bearer ngm_live_YOUR_KEY' }
});
const body = await res.json();
if (!body.success) {
if (body.error.code === 'QUOTA_EXCEEDED') {
console.warn('Quota exhausted. Resets at:', body.meta.reset_at);
} else if (body.error.code === 'PLAN_REQUIRED') {
console.error(`Upgrade to ${body.error.required_plan} to use this endpoint.`);
} else {
console.error('API error:', body.error.message);
}
} else {
// body.data contains the endpoint payload
console.log('Remaining calls:', body.meta.calls_remaining);
}
For a full list of error codes and how to resolve each one, see Errors.