Monitoring API · v1.0.0

Endpoint & error reference

All five endpoints in one place — create, list, retrieve, cancel, alerts — and the error shape.

Livehttps://api.offendersearch.appSandboxhttps://sandbox.offendersearch.app

The five endpoints

Every request authenticates with the X-API-Key header. Base URL https://api.offendersearch.app. Each endpoint below has a Request table and a Response table listing every field; objects that live on their own page — The Monitor object and the alert object — are linked, not repeated.

MethodPathWhat it does
POST/v1/monitorsCreate a monitor.
GET/v1/monitorsList monitors.
GET/v1/monitors/{monitorId}Retrieve a monitor.
DELETE/v1/monitors/{monitorId}Cancel a monitor.
GET/v1/monitors/{monitorId}/alertsAlert history.

POST /v1/monitors — create monitor request and response fields

POST/v1/monitorsAuth: X-API-Key

Create a person or location monitor on the sex offender or criminal dataset. Returns the new monitor with 201.

Request

Body · application/json
FieldTypeDescription
product
required
string
one of "sex-offender", "criminal"
The dataset this monitor watches. One product per monitor: watching one person in both datasets is two monitors, billed separately.
Example "sex-offender"
type
required
string
one of "person", "location"
The predicate. person watches a name (and date of birth); location watches a radius around a point. criminal with location returns 200 not_yet_available and creates nothing.
Example "person"
person
optional
PersonCriteria or nullRequired when type is person; ignored otherwise.
location
optional
LocationCriteria or nullRequired when type is location; ignored otherwise.
minConfidence
optional
string or null
one of "dob_match", "year_match", "age_match", "name_match", "any"
The weakest match strength a person monitor alerts on, strongest first: dob_match, year_match, age_match, name_match. Unset or any applies the default floor: year_match when person.dob is set, name_match when it is not. Location monitors alert on every record in the radius and do not read this field. Any other value is a 422.
Example "dob_match"
label
optional
string or nullYour own name for the monitor. Echoed back on the monitor and in the alert email and webhook (monitorLabel).
Example "Jordan Rivera — SO watch"
channels
optional
ChannelsWhere alerts go. Send at least one email address or a webhookUrl, or the request is a 422.

Response

201 · application/json

The monitor was created and is active.

The body is the Monitor object. One standing watch, as POST /v1/monitors, GET /v1/monitors and GET /v1/monitors/{monitorId} return it. A person monitor carries person and no location key; a location monitor carries location and no person key — read type, then the matching object.

200 · application/json

product: "criminal" with type: "location". No monitor was created and nothing is billed; branch on status.

FieldTypeDescription
status
string
one of "not_yet_available"
Always not_yet_available.
message
stringA sentence you can show a user.
Errors
StatusCodeWhen
401—No valid X-API-Key header (or dashboard session token). Body: the Error object, detail a sentence.
402—The account has no active subscription and no active free trial.
422—Validation failed. detail is a sentence naming the field for an unknown product, type or minConfidence, no channel, a person monitor without person.lastName, a person.dob that is not YYYY-MM-DD, a location monitor without location.address or lat+lng, or radiusMiles outside (0, 100]. A missing product or type, or a wrongly typed field, returns detail as a list of {type, loc, msg} objects.
POST /v1/monitors
curl -X POST "https://api.offendersearch.app/v1/monitors" \
  -H "X-API-Key: $OFFENDERSEARCH_KEY" -H "Content-Type: application/json" \
  -d '{ "product": "sex-offender", "type": "person",
        "person": { "firstName": "Jordan", "lastName": "Rivera", "dob": "1988-04-12" },
        "channels": { "email": "alerts@example.com" } }'
A POST for product: "criminal" with type: "location" returns a 200 with status: "not_yet_available" — no monitor is created and nothing is billed. See Location monitoring.

GET /v1/monitors — list monitors request and response fields

GET/v1/monitorsAuth: X-API-Key

Every monitor on the account, newest first. Active monitors only unless you pass includeCanceled=true.

Request

Query parameters
FieldTypeDescription
includeCanceled
optional · default false
booleantrue also returns canceled monitors.

Response

200 · application/json

The monitors.

FieldTypeDescription
monitors
array of MonitorThe account's monitors, newest createdAt first. [] when there are none.
Errors
StatusCodeWhen
401—No valid X-API-Key header (or dashboard session token). Body: the Error object, detail a sentence.
402—The account has no active subscription and no active free trial.
200 OK
{
  "monitors": [
    { "id": "mon_b8f40d7afb9dc0d8", "product": "sex-offender", "type": "person",
      "minConfidence": null, "label": "Jordan Rivera — SO watch", "status": "active",
      "channels": { "emails": ["alerts@example.com"] },
      "createdAt": "2026-09-05T14:02:11+00:00", "canceledAt": null,
      "person": { "firstName": "Jordan", "lastName": "Rivera", "dob": "1988-04-12" } }
  ]
}

GET /v1/monitors/{id} and /alerts

GET /v1/monitors/{id} returns one monitor with its ten most recently observed alerts in recentAlerts; GET /v1/monitors/{id}/alerts returns its alert history, up to 200 alerts per call (limit, default 50). Both are scoped to the creating account; another account’s id returns 404. The fields are defined on The Monitor object and Alerts.

GET /v1/monitors/{id} — retrieve monitor request and response fields

GET/v1/monitors/{monitorId}Auth: X-API-Key

One monitor with recentAlerts, its ten most recently observed alerts. Works on active and canceled monitors.

Request

Path parameters
FieldTypeDescription
monitorId
required
stringThe monitor id (mon_…). Another account's monitor id is a 404.
Example "mon_b8f40d7afb9dc0d8"

Response

200 · application/json

The monitor, including recentAlerts.

The body is the Monitor object. One standing watch, as POST /v1/monitors, GET /v1/monitors and GET /v1/monitors/{monitorId} return it. A person monitor carries person and no location key; a location monitor carries location and no person key — read type, then the matching object.

Errors
StatusCodeWhen
401—No valid X-API-Key header (or dashboard session token). Body: the Error object, detail a sentence.
402—The account has no active subscription and no active free trial.
404—No monitor with this id on your account: {"detail": "Monitor not found."}.

DELETE /v1/monitors/{id} — cancel monitor request and response fields

DELETE/v1/monitors/{monitorId}Auth: X-API-Key

Cancel a monitor. It stops being evaluated at once and is not charged on any invoice prepared after the cancel. The monitor and its alerts stay readable with GET /v1/monitors/{monitorId}.

Request

Path parameters
FieldTypeDescription
monitorId
required
stringThe monitor id (mon_…). Another account's monitor id is a 404.
Example "mon_b8f40d7afb9dc0d8"

Response

200 · application/json

The monitor is now canceled.

FieldTypeDescription
status
string
one of "canceled"
Always canceled.
id
stringThe canceled monitor's id.
note
stringA fixed sentence about when billing ends. Evaluation stops as soon as the monitor is canceled.
Errors
StatusCodeWhen
401—No valid X-API-Key header (or dashboard session token). Body: the Error object, detail a sentence.
402—The account has no active subscription and no active free trial.
404—No monitor with this id on your account: {"detail": "Monitor not found."}.
409personal_alertThe monitor is a personal alert paid by its own subscription; it is canceled from Alerts in the personal dashboard. detail is {code, message}.

A canceled monitor stops being evaluated at once and stays readable, so its alert history is preserved. See Billing.

200 OK
{
  "status": "canceled",
  "id": "mon_b8f40d7afb9dc0d8",
  "note": "Monitoring stops and billing ends at the close of the current cycle."
}

The error envelope

Every monitoring error is a JSON object with one key, detail. For most errors detail is a sentence you can show a user. A body that fails type validation (a missing product, a string where a number belongs) returns detail as a list of { type, loc, msg } objects, where loc is the path to the field. Branch on the HTTP status; read detail for the reason. The shape is the Error object shared by every OffenderSearch API.

422 · a rule
{
  "detail": "channels must include at least one email or a webhookUrl."
}
422 · a missing field
{
  "detail": [
    { "type": "missing", "loc": ["body", "product"], "msg": "Field required",
      "input": { "type": "person" } }
  ]
}
HTTPWhen you’ll see it
401No valid X-API-Key header (or dashboard session token).
402The account has no active subscription and no active free trial.
404No monitor with that id on your account — including another account’s monitor id.
409DELETE on a personal alert, which is billed by its own subscription. detail is { code: "personal_alert", message }.
422The create body failed validation. detail is a sentence naming the field, or a list of { type, loc, msg } objects for a missing or wrongly typed field.

The monitoring endpoints do not return 429. Apply your own client-side concurrency control.

Monitoring alerts are not a consumer report, and monitoring is not part of FCRA Partner Access. Every alert email carries that notice in its footer.

Product overview