US NHTSA Vehicle Recall Monitor avatar

US NHTSA Vehicle Recall Monitor

Pricing

$4.00 / 1,000 result items

Go to Apify Store
US NHTSA Vehicle Recall Monitor

US NHTSA Vehicle Recall Monitor

Query and monitor official NHTSA vehicle safety recalls by vehicle or campaign.

Pricing

$4.00 / 1,000 result items

Rating

0.0

(0)

Developer

hugo liu

hugo liu

Maintained by Community

Actor stats

0

Bookmarked

2

Total users

1

Monthly active users

5 hours ago

Last modified

Categories

Share

Query and monitor official U.S. National Highway Traffic Safety Administration (NHTSA) vehicle recalls by campaign number or vehicle identity. Get normalized, traceable recall rows with manufacturer, affected component, remedy, report date, safety flags, and an official source URL.

Use it for fleet and dealer checks, vehicle-safety research, compliance feeds, automotive data products, and scheduled recall monitoring. It is a focused wrapper around NHTSA's structured APIs: easy to run, predictable to integrate, and explicit about what a vehicle-level recall lookup can—and cannot—prove.

Before you run

  • For a one-off API call, use lookup or export. monitor is stateful and emits only new or changed rows after the monitor snapshot is established.
  • Actor usage costs $0.004 per result, equivalent to $4 per 1,000 results, under Pay Per Event pricing. Runs with zero results have no result-item usage charge. See the Pricing tab for the current terms.
  • Data is returned from NHTSA at fetch time. This Actor does not provide a real-time freshness guarantee or an SLA for upstream publication delays.
  • Start with an exact campaignNumber or a specific make + model + modelYear and a small maxResults. A make + modelYear query first enumerates models and then queries them serially; maxResults: 1 does not avoid model enumeration, and an empty sweep may still contact every model. maxResults: 0 can fan out across all enumerated models and is not an unlimited historical archive.
  • Successful runs have a per-run Dataset. This Actor does not automatically rename it; retain the returned Dataset ID or name/copy important results before relying on your account's default retention policy.

What this Actor does

  • Looks up an exact NHTSA campaign number.
  • Looks up recalls for one make + model + modelYear vehicle line.
  • Discovers NHTSA-recognized models for a make + modelYear, then queries each model with the same bounded result limit.
  • Filters normalized records by campaign number and inclusive report-date windows.
  • Normalizes dates, vehicle identity, booleans, missing values, and source URLs into a stable Dataset contract.
  • Supports current lookup, bounded export, and incremental monitor modes.
  • Emits CURRENT, ADDED, or UPDATED rows with changedFields, a content hash, and a stable idempotency key.

Why teams use it

NHTSA recall data is most useful when campaign details and operational flags are available in a single, automation-ready row. This Actor removes repetitive API plumbing and preserves the official context needed for a fleet dashboard, customer workflow, research dataset, or AI agent.

Common use cases:

  • Check the current recall campaigns for a make, model, and model year.
  • Retrieve one campaign for a compliance or service workflow.
  • Export a historical report-date window for research.
  • Schedule a stable vehicle scope and alert only when a record is new or changed.

Data source and lookup scope

The Actor uses the official NHTSA vehicle safety APIs:

Input shapeOfficial endpointBehavior
campaignNumber/recalls/campaignNumberExact campaign lookup; takes precedence over vehicle fields
make + model + modelYear/recalls/recallsByVehicleOne recall query for the exact vehicle line
make + modelYear/products/vehicle/models, then /recalls/recallsByVehicleEnumerates NHTSA-recognized models and queries each one

NHTSA is a structured lookup API. This Actor does not provide arbitrary full-text recall search, manufacturer-text search, VIN decoding, ownership history, or a VIN-level determination that a particular vehicle is affected. A make/year query can create multiple upstream requests; start with a specific model or campaign and a small maxResults.

Request and resource notes

  • An exact campaignNumber lookup makes one campaign request. An exact make + model + modelYear lookup makes one vehicle request.
  • A make + modelYear lookup makes one model-enumeration request followed by one recall request per returned model, serially. With maxResults > 0, the Actor can stop after enough normalized rows; with no matches it may query all enumerated models.
  • maxResults limits normalized rows after source filtering. It is not a request-count, latency, or cost guarantee, and maxResults: 0 removes only the Actor-side row cap.
  • sourceRecordId includes campaign, make, model, and model year. The same campaign found through different query shapes can therefore have a different row identity; for cross-call deduplication prefer campaignNumber, or use it with normalized vehicle fields when vehicle scope matters.
  • The boolean safety fields are normalized with strict source semantics: false means the source value was not true; it is not confirmation that a vehicle is safe or that no precaution is needed.

Run modes

ModeWhat it returnsState behavior
lookupMatching current records as CURRENTDoes not read or change monitor state
exportA bounded current-source date-window result as CURRENTDoes not read or change monitor state
monitorNew and changed records as ADDED or UPDATEDReads and updates the named Key-Value Store

Use lookup for a focused check, export for a defined report, and monitor for recurring change detection. The default mode is monitor, although a campaign or vehicle scope is still required.

Quick start

Apify Console

  1. Open the Actor and select Input.
  2. Enter either campaignNumber, or make plus modelYear (with optional model).
  3. Choose lookup, export, or monitor.
  4. Add a report-date window and keep maxResults small for the first run.
  5. Click Start, then inspect the Dataset or download JSON, CSV, or Excel from the Output tab.

Apify CLI

After installing and authenticating the Apify CLI, look up one campaign:

apify call <ACTOR_ID> \
--input '{"mode":"lookup","campaignNumber":"26V123000","maxResults":1}' \
--output-dataset

Or query one vehicle line:

apify call <ACTOR_ID> \
--input '{"mode":"lookup","make":"Honda","model":"Civic","modelYear":"2023","maxResults":10}' \
--output-dataset

<ACTOR_ID> can be the Actor ID or an authorized Actor name. A valid campaign or vehicle query with no matches completes successfully with zero Dataset items.

REST API

Start a run with a JSON request body:

curl -X POST \
-H "Authorization: Bearer $APIFY_TOKEN" \
-H "Content-Type: application/json" \
--data '{
"mode": "lookup",
"make": "Honda",
"model": "Civic",
"modelYear": "2023",
"maxResults": 25
}' \
"https://api.apify.com/v2/acts/<ACTOR_ID>/runs?waitForFinish=60"

Read the returned defaultDatasetId through the Dataset API:

GET https://api.apify.com/v2/datasets/<DATASET_ID>/items?format=json&clean=true
GET https://api.apify.com/v2/datasets/<DATASET_ID>/items?format=csv&clean=true&attachment=true
GET https://api.apify.com/v2/datasets/<DATASET_ID>/items?format=xlsx&clean=true&attachment=true

Use limit and offset for pagination. Keep $APIFY_TOKEN in an environment variable; never put it in Actor input, source code, logs, or Dataset records.

API run lifecycle

The POST request starts an Apify run; it does not return Dataset rows directly. If waitForFinish=60 returns a non-terminal status such as RUNNING, keep the returned runId and poll GET /v2/actor-runs/<RUN_ID> or use a Webhook. Read defaultDatasetId after the run reaches SUCCEEDED. A successful empty Dataset is valid; in monitor mode it can mean that no recall changed, not that NHTSA had no matching recall.

Input API reference

The input is a JSON object. The ./.actor/input_schema.json is the machine-readable contract used by the Console and API.

FieldType / defaultDescription
modeenum, "monitor"monitor, lookup, or export.
campaignNumberstringNHTSA campaign in the form two digits, one letter, six digits, for example 23V769000. When present, it overrides vehicle lookup. Punctuation and letter case are normalized for validation.
makestringVehicle make, used with modelYear.
modelstringOptional vehicle model. Omit it to enumerate models for the make/year.
modelYearfour-digit stringModel year from 1900 through 2100, used with make.
recalledSinceYYYY-MM-DDInclusive lower bound for NHTSA ReportReceivedDate.
recalledUntilYYYY-MM-DDInclusive upper bound for ReportReceivedDate.
maxResultsinteger, 500Maximum emitted rows. Range: 025000; 0 removes the Actor-side cap after source queries and filtering, but does not limit make/year fan-out.
emitInitialSnapshotboolean, trueIn monitor, emit first-seen records as ADDED; set false to seed state without emitting the initial snapshot.
monitorIdstringOptional stable namespace for separate monitors sharing a state store.
stateStoreNamestring, "us-nhtsa-monitor-state"Named Apify Key-Value Store used for monitor fingerprints.

Query behavior and validation

  • Provide campaignNumber, or provide make and modelYear. A model is optional for a whole-make/model-year sweep.
  • Dates must be real calendar dates in YYYY-MM-DD; invalid dates such as 2026-02-30 are rejected.
  • recalledSince cannot be after recalledUntil.
  • campaignNumber is validated against the NHTSA campaign shape, such as 23V769000.
  • Filtering is applied after source normalization and before maxResults.
  • For make/year sweeps, model enumeration and upstream recall requests still occur according to the lookup scope even when maxResults is small.
  • Records without a campaign number are discarded because they cannot provide a stable source identity.
  • A valid query with no matches returns SUCCEEDED with an empty Dataset. Invalid input, malformed API JSON, or an unrecoverable HTTP error fails the run with an explanatory message.

Example inputs

Monitor one campaign

{
"mode": "monitor",
"campaignNumber": "26V123000",
"maxResults": 1,
"monitorId": "campaign-26V123000"
}

Look up one current vehicle line

{
"mode": "lookup",
"make": "Honda",
"model": "Civic",
"modelYear": "2023",
"maxResults": 10
}

Export a historical vehicle-recall window

{
"mode": "export",
"make": "Ford",
"modelYear": "2022",
"recalledSince": "2015-01-01",
"recalledUntil": "2015-12-31",
"maxResults": 250
}

Valid empty result and invalid input

An exact lookup for a campaign with no NHTSA rows is valid and returns an empty Dataset:

{
"mode": "lookup",
"campaignNumber": "26V658000",
"maxResults": 1
}

An input such as {"make":"Honda"} is rejected because modelYear is required for a vehicle lookup. An input such as {"campaignNumber":"not-a-campaign"} is rejected before the API is called.

For abnormal upstream behavior, the Actor retries bounded transient failures such as 429, 5xx, network errors, and timeouts. Malformed API JSON and other unrecoverable responses fail the run with an explanatory error; they are not silently converted to an empty Dataset.

Output API reference

Each Dataset item is one normalized NHTSA recall record. Empty source values are represented by empty strings, false booleans, or null dates according to the field contract.

Representative historical recall output

This trimmed example is based on a real NHTSA recall record. Hash values and timestamps are placeholders for the values generated by the run; the complete row contains every field listed below.

{
"source": "nhtsa",
"sourceRecordId": "recall:15V123000:KIA:SOUL:2014",
"recordType": "recall",
"campaignNumber": "15V123000",
"actionNumber": "",
"manufacturer": "Kia Motors America",
"make": "KIA",
"model": "SOUL",
"modelYear": "2014",
"component": "VEHICLE SPEED CONTROL:ACCELERATOR PEDAL",
"potentialUnitsAffected": "208858",
"summary": "Kia Motors America is recalling certain model year 2014-2015 Soul vehicles; a section of the accelerator pedal may bend and fracture.",
"consequence": "A bent or broken accelerator pedal may make it difficult to accelerate, increasing the risk of a crash.",
"remedy": "Kia will notify owners and dealers will add a supporting rubber underneath the pedal stopper, free of charge.",
"reportReceivedDate": "2015-03-02",
"doNotDrive": false,
"parkOutside": false,
"overTheAirUpdate": false,
"sourceUrl": "https://www.nhtsa.gov/recalls?nhtsaId=15V123000",
"changeType": "CURRENT",
"changedFields": [],
"detectedAt": "2026-09-02T00:00:00.000Z",
"contentHash": "<sha256>",
"idempotencyKey": "<sha256>"
}

The three boolean flags are source indicators, not a VIN-level safety assessment. For monitor, the same content fields are accompanied by ADDED or UPDATED; changedFields lists normalized fields that changed since the prior snapshot. CURRENT is used by lookup and export.

Identity and monitor metadata

FieldTypeDescription
sourcestringAlways nhtsa.
sourceRecordIdstringStable identity for a vehicle-scoped row in the form recall:<campaign>:<make>:<model>:<modelYear>. For cross-query deduplication, prefer campaignNumber because the same campaign can appear with different vehicle scope.
recordTypestringAlways recall.
changeTypestringADDED, UPDATED, or CURRENT.
changedFieldsstring[]Normalized fields changed since the previous monitor snapshot; empty for ADDED and CURRENT.
detectedAtISO timestampTime this Actor produced the row.
contentHashstringSHA-256 hash of the normalized source snapshot, excluding derived monitor metadata.
idempotencyKeystringStable key for monitor scope, source record, and content version. Use it to deduplicate retries.

Recall fields

FieldTypeDescription
campaignNumberstringOfficial NHTSA campaign number.
actionNumberstringNHTSA action number when supplied.
manufacturerstringManufacturer named by NHTSA.
makestringVehicle make.
modelstringVehicle model.
modelYearstringVehicle model year.
componentstringAffected vehicle component.
potentialUnitsAffectedstringReported potentially affected units.
summarystringRecall summary.
consequencestringReported safety consequence.
remedystringReported remedy.
notesstringAdditional NHTSA notes.
reportReceivedDatestring or nullNormalized NHTSA report date in YYYY-MM-DD.
doNotDrivebooleanNHTSA parkIt safety flag.
parkOutsidebooleanNHTSA parkOutSide safety flag.
overTheAirUpdatebooleanWhether an over-the-air update is indicated.
sourceUrlstringOfficial NHTSA recall page for the campaign.

The Actor pushes structured JSON rows only. Apify generates these views from the same Dataset:

  • JSON: .../items?format=json&clean=true
  • CSV: .../items?format=csv&clean=true&attachment=true
  • Excel: .../items?format=xlsx&clean=true&attachment=true

Successful non-empty runs have their own Dataset ID. If long-term retention is required, name or copy the Dataset after the run; this Actor does not merge separate runs into a shared output Dataset. Dataset lifetime follows the retention rules of your Apify account and plan; do not treat an unnamed per-run Dataset as a permanent archive.

Monitoring and delivery semantics

In monitor mode:

  1. Records are normalized and deduplicated by sourceRecordId.
  2. The Actor compares normalized content with the snapshot in the named Key-Value Store.
  3. New records become ADDED; changed records become UPDATED with changedFields.
  4. Dataset delivery completes before the checkpoint is written.

This is safe at-least-once delivery. If Dataset delivery succeeds but the checkpoint write fails, a later run may emit the same event again; downstream consumers should deduplicate with idempotencyKey. Records absent from a later source response are not emitted as REMOVED, because absence may reflect model enumeration, filtering, upstream coverage, or source-window behavior rather than an official withdrawal.

For scheduled monitoring, keep the same monitorId, stateStoreName, and query scope so later runs compare against the same snapshot.

The HTTP layer starts requests serially within one process, waits one second by default between request starts, retries transient network errors, 429, and 5xx responses with bounded exponential backoff and jitter, and honors Retry-After when supplied. These locks and limits are process-local; they do not provide account-wide rate limiting or cross-container exactly-once delivery.

Reliability and limitations

  • NHTSA endpoints can change fields, throttle requests, or have maintenance windows. The Actor retries transient failures within a finite budget.
  • A make/year query depends on the model names currently returned by NHTSA; spelling changes or incomplete model enumeration can affect coverage.
  • A recall is reported by NHTSA for a make/model/year scope. It is not proof of eligibility for a particular VIN, and this Actor does not verify repair completion or ownership.
  • false in doNotDrive, parkOutside, or overTheAirUpdate is not a safety clearance; it means the normalized source flag was not true.
  • The Actor reports what NHTSA publishes. It does not independently verify defect claims, remedy effectiveness, or legal status.
  • A local process lock is not a distributed lock. Strict cross-container coordination would require a shared transactional store and global limiter.

Local development

Requirements: Node.js 20 or newer.

npm install
npm test
npm run build
apify validate-schema
npm run test:real

npm test uses deterministic fixtures and injected failures, including malformed JSON, 429/Retry-After, 5xx, timeout, rate limiting, state ordering, and delivery failure. The bounded real smoke script checks a current campaign, a historical campaign, a valid empty result, and output identity/date fields; it is not an unbounded vehicle-recall export.

Attribution

This Actor consumes public NHTSA data. Review the current NHTSA API terms, availability, and usage guidance before operating at scale. Preserve sourceUrl and campaignNumber when passing records downstream so users can inspect the authoritative recall notice.