# Dealer inventory

## Endpoint

```
GET https://api.motorsdynamic.com/api/v2/dealers/{domainId}/inventory
```

## Plan and price

| Plan | Access | Price |
| --- | --- | --- |
| Free | No | not included |
| Growth | No | not included |
| Scale | No | not included |
| Enterprise | Yes | contract |

A call is billed when it answers 2xx. See [pricing](https://developers.motorsdynamic.com/pricing.md).

## Parameters

| Name | In | Type | Required | Description |
| --- | --- | --- | --- | --- |
| `domainId` | path | integer | yes | Site id (`id` from GET /dealers). |
| `condition` | query | `new` or `used` or `cpo` | no |  |
| `make` | query | string | no | Case-insensitive exact match. |
| `model` | query | string | no | Case-insensitive exact match. |
| `year_min` | query | integer | no |  |
| `year_max` | query | integer | no |  |
| `price_min` | query | number | no |  |
| `price_max` | query | number | no |  |
| `powertrain` | query | `gas` or `diesel` or `hybrid` or `phev` or `electric` or `hydrogen` or `unknown` | no |  |
| `sort` | query | `last_seen_at` or `first_seen_at` or `price` or `year` or `mileage` | no |  |
| `order` | query | `asc` or `desc` | no |  |
| `limit` | query | integer | no |  |
| `cursor` | query | string | no | `page.next_cursor` from the previous page, unchanged. |

## Example request

curl:

```bash
curl "https://api.motorsdynamic.com/api/v2/dealers/101/inventory?condition=new&make=Honda&year_min=2024&limit=1" \
  -H "x-api-key: $MD_API_KEY"
```

JavaScript:

```javascript
const res = await fetch("https://api.motorsdynamic.com/api/v2/dealers/101/inventory?condition=new&make=Honda&year_min=2024&limit=1", {
  headers: { "x-api-key": process.env.MD_API_KEY },
});
if (!res.ok) throw new Error(`${res.status} ${(await res.json()).error}`);
const data = await res.json();
console.log(data);
```

Python:

```python
import os, requests

res = requests.get(
    "https://api.motorsdynamic.com/api/v2/dealers/101/inventory?condition=new&make=Honda&year_min=2024&limit=1",
    headers={"x-api-key": os.environ["MD_API_KEY"]},
    timeout=10,
)
res.raise_for_status()
print(res.json())
```

## Example response

```json
{
  "data": [
    {
      "id": 5501,
      "vin": "1HGCV1F34RA000001",
      "domain_id": 101,
      "url": "https://www.alphahonda.com/new/2024-honda-accord-1HGCV1F34RA000001",
      "stock_number": "H1234",
      "condition": "new",
      "condition_raw": "New",
      "is_cpo": false,
      "year": 2024,
      "make": "Honda",
      "model": "Accord",
      "trim": "EX",
      "body_type": "Sedan",
      "exterior_color": "Platinum White Pearl",
      "interior_color": "Black",
      "drivetrain": "FWD",
      "transmission": "CVT",
      "engine": "1.5L I4 Turbo",
      "fuel_type": "Gasoline",
      "powertrain": "gas",
      "mileage": 8,
      "price": 31250,
      "msrp": 32895,
      "sale_price": null,
      "price_basis": null,
      "price_flags": [],
      "image_count": 32,
      "primary_image": "https://images.example.com/a.jpg",
      "status": "active",
      "first_seen_at": "2026-09-01T12:00:00.000000Z",
      "freshness": {
        "last_seen_at": "2026-09-24T10:00:00.123456Z",
        "observed_at": "2026-09-24T10:00:00.123456Z",
        "age_seconds": 3600
      },
      "provenance": {
        "source": "md_legacy",
        "adapter_version": null,
        "run_id": null,
        "episode": null
      }
    }
  ],
  "page": {
    "limit": 1,
    "has_more": true,
    "next_cursor": "eyJ2IjoxfQ"
  },
  "meta": {
    "domain_id": 101,
    "sort": "last_seen_at",
    "order": "desc"
  }
}
```

## Response fields

| Field | Type | Description |
| --- | --- | --- |
| `data[]` | array of object |  |
| `data[].id` | integer | Stable listing id (same as /v1 vehicles.id). |
| `data[].vin` | string |  |
| `data[].domain_id` | integer |  |
| `data[].url` | string |  |
| `data[].stock_number` | string or null |  |
| `data[].condition` | `new` or `used` or `cpo` or `null` |  |
| `data[].condition_raw` | string or null |  |
| `data[].is_cpo` | boolean |  |
| `data[].year` | integer or null |  |
| `data[].make` | string or null |  |
| `data[].model` | string or null |  |
| `data[].trim` | string or null |  |
| `data[].body_type` | string or null |  |
| `data[].exterior_color` | string or null |  |
| `data[].interior_color` | string or null |  |
| `data[].drivetrain` | string or null |  |
| `data[].transmission` | string or null |  |
| `data[].engine` | string or null |  |
| `data[].fuel_type` | string or null |  |
| `data[].powertrain` | string or null |  |
| `data[].mileage` | integer or null |  |
| `data[].price` | number or null | Advertised price. |
| `data[].msrp` | number or null |  |
| `data[].sale_price` | number or null |  |
| `data[].price_basis` | string or null | How the v2 adapter derived the price (v2 sites only). |
| `data[].price_flags[]` | array of string | `suspect_teamvelocity`: legacy Team Velocity price, known to be wrong on most such sites. |
| `data[].image_count` | integer |  |
| `data[].primary_image` | string or null |  |
| `data[].status` | `active` |  |
| `data[].first_seen_at` | string or null | RFC 3339 UTC with microseconds. |
| `data[].freshness` | object |  |
| `data[].freshness.last_seen_at` | string or null | RFC 3339 UTC with microseconds. |
| `data[].freshness.observed_at` | string or null | RFC 3339 UTC with microseconds. |
| `data[].freshness.age_seconds` | integer or null |  |
| `data[].provenance` | object |  |
| `data[].provenance.source` | `v2` or `md_legacy` |  |
| `data[].provenance.adapter_version` | string or null |  |
| `data[].provenance.run_id` | integer or null |  |
| `data[].provenance.episode` | integer or null |  |
| `page` | object |  |
| `page.limit` | integer |  |
| `page.has_more` | boolean |  |
| `page.next_cursor` | string or null |  |
| `meta` | object |  |

## Errors

| Status | Code | When |
| --- | --- | --- |
| 400 | `invalid_parameter` | A parameter is missing or malformed. The message names it. |
| 401 | `invalid_api_key` | The key is missing, revoked or mistyped. |
| 402 | `plan_required` | The endpoint is on a higher plan. The body names the plan and links to the upgrade. |
| 403 | `not_entitled` | The key may not read this dealer or source. |
| 429 | `rate_limited or quota_exceeded` | Slow down (see `Retry-After`), or the Free monthly calls are used up. |
| 504 | `query_timeout` | The query passed its 4 second budget. Narrow the filters. Not billed. |

Every error has the same body: `{ "error": "<code>", "message": "..." }`. Full list: [errors](https://developers.motorsdynamic.com/docs/errors.md).
