Server-to-server REST API for SecreTag package tracking integrations.
On this page
Getting started
Ask SecreTag support for an API key at support@secretag.co. A test key starts with st_test_, a live key with st_live_.
Pick the host: https://sandbox-api.secretag.co with a test key while you build, https://api.secretag.co with a live key.
Make your first call, listing your tags. Replace API_KEY with your test key.
curl -X GET "https://sandbox-api.secretag.co/v1/integrations/tags" \
-H "X-API-Key: API_KEY"
Read the answer: every JSON answer is the same response envelope, with your result in data when success is true and a message in error when it is false.
Authentication
Every operation takes an organization-scoped API key in the X-API-Key header. Keys are issued by SecreTag support (support@secretag.co); there is no self-serve key page yet. A live key starts with st_live_ and works only on https://api.secretag.co; a test key starts with st_test_ and works only on https://sandbox-api.secretag.co. A missing, unknown or revoked key, or a key used on the other host, answers 401 Invalid API key.
Response envelope
Every JSON answer, success or error, is { "success": boolean, "data": <payload or null>, "error": <message or null> }. Two answers are not wrapped: GET /v1/integrations/disputes/{id}/evidence/pdf returns the PDF bytes (application/pdf) and DELETE /v1/integrations/webhooks/{id} returns 204 with no body.
Tenancy
A caller sees only its own organization's tags and what belongs to them (their shipments, disputes and alerts, the address scores it requested and its own webhook subscriptions); any other id answers 404.
Limits and errors
Failed authentication: after 60 failed attempts in a minute from one IP address, further invalid keys answer 429 Too many failed authentication attempts, try again in a minute.
Organization rate limit: 600 requests per minute per organization; past it, 429 Rate limit exceeded: 600 requests per minute.
Request body: at most 1 MB; a larger body answers 413 Request body too large (limit 1 MB). A JSON body that does not parse answers 400 Malformed JSON.
Every operation that reaches the tracking network (all but the webhook subscription operations and test_webhook) may answer 502 Upstream unavailable (the tracking network timed out, could not be reached or failed) and 503 Upstream not configured (the environment is not connected to the tracking network). Nothing is retried on the request path.
Lists
The four list operations (list_tags, list_shipments, list_alerts, list_disputes) accept only their documented filters; any other query parameter is ignored. page is 1-based (default 1) and limit is 1 to 200 (default 50); any other value answers 400. A filter that matches more than 5,000 items on the tracking network, or a list that takes more than 20 seconds to read, answers 503 List too large, add filters: narrow the filters and retry.
Declared value insurance
A shipment can carry a declared value: send "insurance": { "declared_value": "1250.00", "currency": "USD" } on create_shipment or update_shipment. declared_value is a decimal string with at most two decimals, greater than zero; currency is your organization's currency (three letters, USD unless SecreTag support set another). SecreTag keeps it and returns insurance (declared_value, currency, declared_at) on every shipment, null when none is declared; "insurance": null on update clears it. No premium, policy or claim is attached in this version.
Webhooks
Webhook subscriptions are SecreTag's own. SecreTag relays the events of your tags, shipments, disputes and alerts to each of your active subscriptions that takes the event (its event_types names it, or is null for every event), as a POST of the event's JSON body with these headers:
X-SecreTag-Signature: sha256=<hex HMAC-SHA256 of the raw body>, keyed with the subscription's secret
X-SecreTag-Event: the event type
X-SecreTag-Delivery: the delivery id
A delivery succeeds only on a 2xx answer. Otherwise it is retried, 8 attempts in all, after waits of 30 s, 2 min, 10 min, 30 min, 1 h, 3 h and 8 h, and then marked failed. target_url must be an HTTPS URL on a public address. Verify the signature over the exact bytes you received, with a constant-time comparison.
Verifying a delivery
Every delivery carries X-SecreTag-Signature: sha256= followed by the hex HMAC-SHA256 of the raw body, keyed with your subscription's secret. Check it over the exact bytes you received, before any JSON parsing, with a constant-time comparison, and refuse the delivery when it does not match.
Ruby
In Ruby, with the standard library (in Rails, pass request.raw_post as the body):
require "openssl"
# header is the X-SecreTag-Signature value, raw_body the bytes you received.
def valid_signature?(secret, raw_body, header)
expected = "sha256=" + OpenSSL::HMAC.hexdigest("SHA256", secret, raw_body)
header = header.to_s
expected.bytesize == header.bytesize &&
OpenSSL.fixed_length_secure_compare(expected, header)
end
Node.js
In Node.js, with the built-in crypto module (in Express, read the body with express.raw()):
const crypto = require("node:crypto");
// header is the X-SecreTag-Signature value, rawBody the bytes you received.
function validSignature(secret, rawBody, header) {
const hex = crypto.createHmac("sha256", secret).update(rawBody).digest("hex");
const expected = Buffer.from("sha256=" + hex);
const given = Buffer.from(String(header ?? ""));
return expected.length === given.length &&
crypto.timingSafeEqual(expected, given);
}
Testing in the sandbox
The sandbox operations (/v1/integrations/sandbox/*) run only on sandbox-api.secretag.co; on api.secretag.co they answer 403 Not available in production, use sandbox-api.secretag.co. Use them to simulate tag events and test your webhook receiver without live hardware.
Integrations
Server-to-server access to your tags, shipments, alerts, disputes and webhook subscriptions. There is no tag-creation operation: tags are hardware that SecreTag assigns to your organization.
GET/v1/integrations/alertsList your organization's alerts.
Request, responses and example of GET /v1/integrations/alerts
Operation list_alerts
Alerts raised on your tags while they were assigned to you. Filters: type, severity, unread_only, read and tag_id. Only the filters documented here are forwarded; any other query parameter is ignored. page is 1-based (default 1) and limit is 1 to 200 (default 50); any other value answers 400. pagination counts only your organization's items. A filter that matches more than 5,000 items on the tracking network, or a list that takes more than 20 seconds to read, answers 503 List too large, add filters: narrow the filters and retry.
Parameters of list_alerts
Query parameters:
Parameters of list_alerts
Name
In
Type
Required
Description
page
query
integer (int32)
No
Page number, 1-based. Default 1.
limit
query
integer (int32)
No
Items per page, 1 to 200. Default 50.
type
query
string, nullable
No
Alert type, for example geofence, delivery, dispute, system, package_separation or gps_carrier_mismatch.
400page or limit is not a positive integer, or limit is over 200
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured, or the list is too large: add filters (List too large, add filters)
Example request of list_alerts
curl -X GET "https://api.secretag.co/v1/integrations/alerts" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
POST/v1/integrations/alerts/read-allMark all your unread alerts as read.
Request, responses and example of POST /v1/integrations/alerts/read-all
Operation mark_all_alerts_read
Computed by SecreTag: each of your organization's unread alerts is marked read, one by one, and marked_read is how many were marked. Reading and updating share a 20 second deadline and the 5,000-item limit; a failure part way answers 502, the alerts already marked stay read, and a retry marks only what is still unread.
Responses of mark_all_alerts_read
200 Your unread alerts marked read; data is { "marked_read": <count> }
data: any
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of mark_all_alerts_read
curl -X POST "https://api.secretag.co/v1/integrations/alerts/read-all" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
GET/v1/integrations/alerts/summaryAlert counts for your organization.
Request, responses and example of GET /v1/integrations/alerts/summary
Operation alert_summary
Computed by SecreTag from your organization's alerts: total is the number of your alerts, unread those without read_at, and critical_unread the unread ones of severity critical. Reading your alerts takes at most 20 seconds and 5,000 items on the tracking network; past either the answer is 502, never a partial count.
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of alert_summary
curl -X GET "https://api.secretag.co/v1/integrations/alerts/summary" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
PATCH/v1/integrations/alerts/{id}/readMark one of your alerts as read.
Request, responses and example of PATCH /v1/integrations/alerts/{id}/read
Operation mark_alert_read
Any id that is not one of your organization's alerts answers 404 and nothing is changed.
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Alert not found, not your organization's, or already read
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your live key, which starts with st_live_
ID: the alert id
GET/v1/integrations/disputesList your organization's disputes.
Request, responses and example of GET /v1/integrations/disputes
Operation list_disputes
Disputes opened on your tags while they were assigned to you. Filters: status, type and tag_id. Only the filters documented here are forwarded; any other query parameter is ignored. page is 1-based (default 1) and limit is 1 to 200 (default 50); any other value answers 400. pagination counts only your organization's items. A filter that matches more than 5,000 items on the tracking network, or a list that takes more than 20 seconds to read, answers 503 List too large, add filters: narrow the filters and retry.
Parameters of list_disputes
Query parameters:
Parameters of list_disputes
Name
In
Type
Required
Description
page
query
integer (int32)
No
Page number, 1-based. Default 1.
limit
query
integer (int32)
No
Items per page, 1 to 200. Default 50.
status
query
string, nullable
No
open, investigating or resolved.
type
query
string, nullable
No
Dispute type: not_delivered, damaged, wrong_location or other.
tag_id
query
string, nullable
No
A tag's uuid, printed ID or BLE identifier. A tag not assigned to your organization returns an empty page.
400page or limit is not a positive integer, or limit is over 200
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured, or the list is too large: add filters (List too large, add filters)
Example request of list_disputes
curl -X GET "https://api.secretag.co/v1/integrations/disputes" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
GET/v1/integrations/disputes/statsDispute statistics for your organization.
Request, responses and example of GET /v1/integrations/disputes/stats
Operation dispute_stats
Computed by SecreTag from your organization's disputes, never forwarded:
total: your disputes. open, investigating and resolved: those with that status (a dispute with another status counts in total only).
shopify_submitted: your disputes that carry a shopify_submitted_at.
avg_resolution_hours: the mean of resolved_at minus opened_at in hours, rounded to two decimals, over your resolved disputes that carry both times; null when none is resolved.
evidence_generated: the number of your disputes for which SecreTag recorded a successful generate_evidence call through this API.
amount_at_risk: the sum of the declared values (insurance.declared_value) of your insured shipments that have an open or investigating dispute, as a number with two decimals, in your organization's currency. A dispute's shipment is your latest shipment carrying the dispute's tag created at or before opened_at; each shipment counts once, and a cleared or replaced declared value does not count.
Reading your disputes takes at most 20 seconds and 5,000 items on the tracking network; past either the answer is 502, never a partial figure.
Responses of dispute_stats
200 Dispute counts and figures for your organization
The sum of the declared values of your insured shipments in an open or investigating dispute, a number with two decimals in your organization's currency.
avg_resolution_hours
number (double), nullable
No
Mean hours from open to resolution, two decimals; null when no dispute is resolved.
evidence_generated
integer (int64)
Yes
Your disputes for which SecreTag recorded a successful generate_evidence call.
investigating
integer (int64)
Yes
open
integer (int64)
Yes
resolved
integer (int64)
Yes
shopify_submitted
integer (int64)
Yes
Your disputes that carry a shopify_submitted_at.
total
integer (int64)
Yes
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of dispute_stats
curl -X GET "https://api.secretag.co/v1/integrations/disputes/stats" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
GET/v1/integrations/disputes/{id}Get one of your disputes.
Request, responses and example of GET /v1/integrations/disputes/{id}
Operation get_dispute
Any id that is not one of your organization's disputes answers 404.
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Dispute not found, or not your organization's
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of get_dispute
curl -X GET "https://api.secretag.co/v1/integrations/disputes/ID" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the dispute id
POST/v1/integrations/disputes/{id}/evidence/generateGenerate the evidence PDF for one of your disputes.
Request, responses and example of POST /v1/integrations/disputes/{id}/evidence/generate
Operation generate_evidence
The evidence report is produced by the tracking network; evidence_pdf_key names where it stored the PDF. Download it with get_evidence_pdf. A successful call counts toward dispute_stats.evidence_generated.
Where the tracking network stored the evidence PDF; download it with get_evidence_pdf.
generated_at
string
Yes
RFC 3339 timestamp of generation.
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Dispute or tag not found, or not your organization's
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured, or evidence storage is unavailable on the tracking network (its 503, passed through)
Example request of generate_evidence
curl -X POST "https://api.secretag.co/v1/integrations/disputes/ID/evidence/generate" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the dispute id
GET/v1/integrations/disputes/{id}/evidence/pdfDownload the evidence PDF for one of your disputes.
Request, responses and example of GET /v1/integrations/disputes/{id}/evidence/pdf
Operation get_evidence_pdf
Returns the PDF bytes as the tracking network rendered them, typed application/pdf and not wrapped in the envelope. Call generate_evidence first: until then this answers 404.
Parameters of get_evidence_pdf
Path parameters:
Parameters of get_evidence_pdf
Name
In
Type
Required
Description
id
path
string (uuid)
Yes
Dispute id
Responses of get_evidence_pdf
200 Evidence PDF
Body: PDF bytes
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 No evidence PDF generated for this dispute, or the dispute is not your organization's
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured, or evidence storage is unavailable on the tracking network (its 503, passed through)
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Dispute not found, not your organization's, or already resolved
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of resolve_dispute
curl -X POST "https://api.secretag.co/v1/integrations/disputes/ID/resolve" \
-H "X-API-Key: API_KEY" \
-H "Content-Type: application/json" \
-d '{
"evidence_score": 85,
"resolution": "Confirmed delivered: package located at rear entrance."
}'
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the dispute id
GET/v1/integrations/shipmentsList your organization's shipments.
Request, responses and example of GET /v1/integrations/shipments
Operation list_shipments
Your organization's shipments, each with its insurance (null when none is declared). Filters: q, carrier, package_id and state. data is always { items, pagination }. Only the filters documented here are forwarded; any other query parameter is ignored. page is 1-based (default 1) and limit is 1 to 200 (default 50); any other value answers 400. pagination counts only your organization's items. A filter that matches more than 5,000 items on the tracking network, or a list that takes more than 20 seconds to read, answers 503 List too large, add filters: narrow the filters and retry.
Parameters of list_shipments
Query parameters:
Parameters of list_shipments
Name
In
Type
Required
Description
q
query
string, nullable
No
Free-text search across master tracking number, order ID, recipient name/email, carrier, and child (package) tracking numbers.
carrier
query
string, nullable
No
Filter by carrier (case-insensitive, e.g. "fedex", "ups", "usps").
package_id
query
string (uuid), nullable
No
Return only the shipment that contains this package ID.
state
query
string, nullable
No
Filter to shipments that have at least one tag with this lifecycle state.
page
query
integer (int32)
No
Page number, 1-based. Default 1.
limit
query
integer (int32)
No
Items per page, 1 to 200. Default 50.
Responses of list_shipments
200 One page of your shipments ({ items, pagination }, always present)
400page or limit is not a positive integer, or limit is over 200
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured, or the list is too large: add filters (List too large, add filters)
Example request of list_shipments
curl -X GET "https://api.secretag.co/v1/integrations/shipments" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
POST/v1/integrations/shipmentsCreate a shipment with one or more packages, linking tags already assigned to the caller's organization.
Request, responses and example of POST /v1/integrations/shipments
Operation create_shipment
Creates a shipment and links your tags as its packages; it does not create tags. carrier and packages (at least one) are required; each packages[].tag_identifier is the printed ID, BLE identifier or uuid of a tag assigned to your organization. An unknown tag, or one that is not yours, answers 404 naming it, and a tag named twice answers 400, both before anything is sent. origin_location_id is not supported and answers 400. Add insurance to declare a value (see the field); null is refused on create. The 201 answer carries insurance. If the tracking network does not answer in time, SecreTag checks whether the shipment was created and answers 201 when it was, 502 otherwise.
Declares a value for the new shipment. Each rule refused answers 400: declared_value a decimal string with at most two decimals, greater than zero; currency equal to your organization's currency. null is refused on create.
master_tracking_number
string, nullable
No
order_id
string, nullable
No
origin_address
string, nullable
No
origin_lat
number (double), nullable
No
origin_lng
number (double), nullable
No
origin_location_id
string (uuid), nullable
No
Not supported by SecreTag: a request that names it answers 400.
400 Validation error or invalid carrier, a tag named twice, origin_location_id, an invalid insurance, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 A tag is not found, or not assigned to your organization
409 A tag is already assigned to another shipment
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Shipment not found, or not your organization's
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of get_shipment
curl -X GET "https://api.secretag.co/v1/integrations/shipments/ID" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the shipment id
PATCH/v1/integrations/shipments/{id}Update one of your shipments.
Request, responses and example of PATCH /v1/integrations/shipments/{id}
Operation update_shipment
Updates the tracking number, carrier, addresses or recipient fields. All fields are optional; omitted fields are left unchanged. insurance sets the declared value and "insurance": null clears it; a body with only insurance changes nothing on the tracking network. The answer carries insurance.
Sets the declared value, replacing any earlier one. Each rule refused answers 400: declared_value a decimal string with at most two decimals, greater than zero; currency equal to your organization's currency. null clears it; omit it to leave it unchanged.
master_tracking_number
string, nullable
No
order_id
string, nullable
No
origin_address
string, nullable
No
origin_lat
number (double), nullable
No
origin_lng
number (double), nullable
No
recipient_email
string, nullable
No
recipient_name
string, nullable
No
recipient_phone
string, nullable
No
service_level
string, nullable
No
Service level (e.g., ground, express, priority, next_day, economy)
The declared value SecreTag keeps for this shipment; null when none is declared. Present on every shipment SecreTag returns.
master_status
string, nullable
No
master_tracking_number
string, nullable
No
order_id
string, nullable
No
organization_id
string (uuid)
Yes
origin_address
string, nullable
No
origin_lat
number (double), nullable
No
origin_lng
number (double), nullable
No
origin_location_id
string (uuid), nullable
No
public_id
string
Yes
recipient_email
string, nullable
No
recipient_name
string, nullable
No
recipient_phone
string, nullable
No
service_level
string, nullable
No
updated_at
string (date-time)
Yes
400 Validation error, an invalid insurance, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Shipment not found, or not your organization's
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your live key, which starts with st_live_
ID: the shipment id
GET/v1/integrations/tagsList your organization's tags.
Request, responses and example of GET /v1/integrations/tags
Operation list_tags
Your organization's tags with their last known location. Filters: state, search, order_id and include_archived. Only the filters documented here are forwarded; any other query parameter is ignored. page is 1-based (default 1) and limit is 1 to 200 (default 50); any other value answers 400. pagination counts only your organization's items. A filter that matches more than 5,000 items on the tracking network, or a list that takes more than 20 seconds to read, answers 503 List too large, add filters: narrow the filters and retry.
400page or limit is not a positive integer, or limit is over 200
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured, or the list is too large: add filters (List too large, add filters)
Example request of list_tags
curl -X GET "https://api.secretag.co/v1/integrations/tags" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
GET/v1/integrations/tags/{id}Get one of your tags.
Request, responses and example of GET /v1/integrations/tags/{id}
Operation get_tag
The tag with ping_count, last_ping and recent_pings.
Parameters of get_tag
Path parameters:
Parameters of get_tag
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
Carrier fields of a tag activated outside a shipment (a self-serve tag).
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Tag not found, or not assigned to your organization
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of get_tag
curl -X GET "https://api.secretag.co/v1/integrations/tags/ID" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
PATCH/v1/integrations/tags/{id}Update one of your tags.
Request, responses and example of PATCH /v1/integrations/tags/{id}
Operation update_tag
Updates the recipient, address, order or metadata fields. All fields are optional; omitted fields are left unchanged. If the tag is linked to a shipment, matching fields are mirrored to the shipment.
Parameters of update_tag
Path parameters:
Parameters of update_tag
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
Per-tag override of the deactivate-after-delivery setting: omit to leave it unchanged, null to inherit the organization default, true or false to force it.
Per-tag override of the organization's deactivate-after-delivery setting; null inherits the organization default.
auto_off_at
string (date-time), nullable
No
The scheduled automatic switch-off time, when known.
auto_off_state
string, nullable
No
active, scheduled or off: the tag's automatic switch-off state; null when not known.
ble_identifier
string
Yes
created_at
string (date-time)
Yes
delivered_at
string (date-time), nullable
No
destination_address
string, nullable
No
destination_lat
number (double), nullable
No
destination_lng
number (double), nullable
No
geofence_radius_m
integer (int32)
Yes
id
string (uuid)
Yes
metadata
object
Yes
network_coverage_months
integer (int32), nullable
No
The network coverage months sold for this tag's device, when known (read only).
network_device_id
string, nullable
No
network_last_checked
string (date-time), nullable
No
network_off_override_at
string (date-time), nullable
No
An explicit network switch-off time set for this tag's device, or null (read only).
order_id
string, nullable
No
organization_id
string (uuid)
Yes
origin_address
string, nullable
No
origin_lat
number (double), nullable
No
origin_lng
number (double), nullable
No
origin_location_id
string (uuid), nullable
No
The origin location the tag was created with, if any (read only).
recipient_email
string, nullable
No
recipient_name
string, nullable
No
recipient_phone
string, nullable
No
shipment_package_id
string (uuid), nullable
No
shipped_at
string (date-time), nullable
No
state
string
Yes
400 Malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Tag not found, or not assigned to your organization
413 Request body too large (limit 1 MB)
422 Validation error
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your live key, which starts with st_live_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
GET/v1/integrations/tags/{id}/disputesList the disputes of one of your tags.
Request, responses and example of GET /v1/integrations/tags/{id}/disputes
Operation list_tag_disputes
Disputes opened on the tag while it was assigned to you: a dispute opened before then is not listed. Only the filters documented here are forwarded; any other query parameter is ignored. page is 1-based (default 1) and limit is 1 to 200 (default 50); any other value answers 400. pagination counts only your organization's items. A filter that matches more than 5,000 items on the tracking network, or a list that takes more than 20 seconds to read, answers 503 List too large, add filters: narrow the filters and retry.
Parameters of list_tag_disputes
Path and query parameters:
Parameters of list_tag_disputes
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
400page or limit is not a positive integer, or limit is over 200
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Tag not found, or not assigned to your organization
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured, or the list is too large: add filters (List too large, add filters)
Example request of list_tag_disputes
curl -X GET "https://api.secretag.co/v1/integrations/tags/ID/disputes" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
GET/v1/integrations/tags/{id}/evidenceGet the evidence data of one of your tags.
Request, responses and example of GET /v1/integrations/tags/{id}/evidence
Operation get_tag_evidence
Everything the evidence PDF of the tag's most recent dispute with generated evidence contains, as JSON: the dispute, delivery metrics, carrier data and location proof. Answers 404 when no evidence has been generated for the tag, and when the tag's evidence belongs to a dispute opened before the tag was assigned to you.
Parameters of get_tag_evidence
Path parameters:
Parameters of get_tag_evidence
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
Responses of get_tag_evidence
200 Full evidence data for the tag's most recent dispute with a generated PDF
Up to 50 most recent BLE location reports, oldest-first.
origin_address
string, nullable
No
pings_at_destination
integer (int64)
Yes
Pings detected within 150 m of the destination coordinates.
tag_count
integer (int64)
Yes
Number of tags in the shipment (> 1 means multi-box).
total_pings
integer (int64)
Yes
Total BLE location reports recorded across all tags in the shipment.
tracking_number
string, nullable
No
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Tag not found or not assigned to your organization, or no evidence has been generated for this tag
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of get_tag_evidence
curl -X GET "https://api.secretag.co/v1/integrations/tags/ID/evidence" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
GET/v1/integrations/tags/{id}/journeyGet the ping journey of one of your tags.
Request, responses and example of GET /v1/integrations/tags/{id}/journey
Operation get_journey
The tag's ping locations, in order. Not paginated.
Parameters of get_journey
Path parameters:
Parameters of get_journey
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Tag not found, or not assigned to your organization
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of get_journey
curl -X GET "https://api.secretag.co/v1/integrations/tags/ID/journey" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
GET/v1/integrations/webhooksList your webhook subscriptions.
Request, responses and example of GET /v1/integrations/webhooks
Operation list_webhooks
SecreTag's own subscriptions for your organization in this environment, active ones first and newest first within each group, as a bare array (not paginated).
array of string, one of tag.state_changed, tag.delivered, tag.approaching, tag.carrier_updated, dispute.opened, dispute.resolved, dispute.evidence_submitted, shipment.created, shipment.delivered, risk.high_score, nullable
No
The event types the subscription takes; null for every event.
id
string (uuid)
Yes
is_active
boolean
Yes
label
string, nullable
No
organization_id
string (uuid)
Yes
target_url
string
Yes
updated_at
string (date-time)
Yes
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
Example request of list_webhooks
curl -X GET "https://api.secretag.co/v1/integrations/webhooks" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
POST/v1/integrations/webhooksCreate a webhook subscription.
Request, responses and example of POST /v1/integrations/webhooks
Operation create_webhook
target_url must be an HTTPS URL on a public address. event_types lists the events to receive; omit it or send null for every event. The ten event types: tag.state_changed, tag.delivered, tag.approaching, tag.carrier_updated, dispute.opened, dispute.resolved, dispute.evidence_submitted, shipment.created, shipment.delivered, risk.high_score. The signing secret is returned once, in this response only: store it. Every delivery carries X-SecreTag-Signature: sha256=<hex HMAC-SHA256 of the raw body> keyed with that secret, with X-SecreTag-Event and X-SecreTag-Delivery. A delivery succeeds only on a 2xx answer and is retried up to 8 attempts in all (waits of 30 s, 2 min, 10 min, 30 min, 1 h, 3 h and 8 h).
array of string, one of tag.state_changed, tag.delivered, tag.approaching, tag.carrier_updated, dispute.opened, dispute.resolved, dispute.evidence_submitted, shipment.created, shipment.delivered, risk.high_score, nullable
No
The event types the subscription takes; null for every event.
id
string (uuid)
Yes
is_active
boolean
Yes
label
string, nullable
No
organization_id
string (uuid)
Yes
secret
string, nullable
No
The signing secret, returned once in this response and never again. Verify each delivery's X-SecreTag-Signature: sha256=<hex HMAC-SHA256 of the raw body> with it.
target_url
string
Yes
updated_at
string (date-time)
Yes
400 target_url missing, not HTTPS or not on a public address, an unknown event type, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
API_KEY: your live key, which starts with st_live_
DELETE/v1/integrations/webhooks/{id}Deactivate one of your webhook subscriptions.
Request, responses and example of DELETE /v1/integrations/webhooks/{id}
Operation delete_webhook
The subscription stops receiving events and its pending deliveries are cancelled. Answers 204 with no body.
Parameters of delete_webhook
Path parameters:
Parameters of delete_webhook
Name
In
Type
Required
Description
id
path
string (uuid)
Yes
Webhook subscription id
Responses of delete_webhook
204 Subscription deactivated
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Subscription not found, or not your organization's
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
API_KEY: your live key, which starts with st_live_
ID: the webhook subscription id
GET/v1/integrations/webhooks/{id}/deliveriesList the deliveries of one of your webhook subscriptions.
Request, responses and example of GET /v1/integrations/webhooks/{id}/deliveries
Operation list_webhook_deliveries
SecreTag's own delivery log for the subscription, newest first. page is 1-based (default 1) and limit is 1 to 200 (default 50); any other value answers 400.
400page or limit is not a positive integer, or limit is over 200
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 Subscription not found, or not your organization's
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
Example request of list_webhook_deliveries
curl -X GET "https://api.secretag.co/v1/integrations/webhooks/ID/deliveries" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
ID: the webhook subscription id
Sandbox
Sandbox-only operations for integration testing: inject mock pings, alerts, disputes and carrier events, force a tag state, reset a tag and send sample webhook events, without live hardware. They run only on sandbox-api.secretag.co; on api.secretag.co they answer 403.
POST/v1/integrations/sandbox/tags/{id}/alertInject a fake alert on one of your sandbox tags.
Request, responses and example of POST /v1/integrations/sandbox/tags/{id}/alert
Operation mock_alert
Creates an alert on the tag so you can test your alert handling. Send {} for an alert of type delivery and severity warning. Valid alert_type: geofence, delivery, dispute, system, package_separation, gps_carrier_mismatch. Valid severity: info, warning, critical. The alert appears in list_alerts.
Parameters of mock_alert
Path parameters:
Parameters of mock_alert
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
400 Invalid alert_type or severity, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
403 Not available in production, use sandbox-api.secretag.co (sandbox operations run only on the sandbox host)
404 Tag not found, or not assigned to your organization
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your test key, which starts with st_test_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
POST/v1/integrations/sandbox/tags/{id}/carrier-eventInject a fake carrier status on the tag's shipment package.
Request, responses and example of POST /v1/integrations/sandbox/tags/{id}/carrier-event
Operation mock_carrier_event
The tag must already be linked to a shipment (through create_shipment); otherwise the answer is 400. Valid status: in_transit, out_for_delivery, delivered, exception.
Parameters of mock_carrier_event
Path parameters:
Parameters of mock_carrier_event
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
Carrier status. One of: in_transit, out_for_delivery, delivered, exception
Responses of mock_carrier_event
200 Carrier status updated on the tag's package; data is { tag_id, package_id, status }
data: any
400 Invalid status, the tag is not linked to a shipment, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
403 Not available in production, use sandbox-api.secretag.co (sandbox operations run only on the sandbox host)
404 Tag not found, or not assigned to your organization
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your test key, which starts with st_test_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
POST/v1/integrations/sandbox/tags/{id}/disputeOpen a fake dispute on one of your sandbox tags.
Request, responses and example of POST /v1/integrations/sandbox/tags/{id}/dispute
Operation mock_dispute
Opens a dispute with status open. Send {} for a not_delivered dispute with a default claim. Valid dispute_type: not_delivered, damaged, wrong_location, other; customer_claim is at most 1000 characters. Use it to test the dispute flow: open, generate evidence, download the PDF, resolve.
Parameters of mock_dispute
Path parameters:
Parameters of mock_dispute
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
400 Invalid dispute_type, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
403 Not available in production, use sandbox-api.secretag.co (sandbox operations run only on the sandbox host)
404 Tag not found, or not assigned to your organization
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of mock_dispute
curl -X POST "https://sandbox-api.secretag.co/v1/integrations/sandbox/tags/ID/dispute" \
-H "X-API-Key: API_KEY" \
-H "Content-Type: application/json" \
-d '{
"customer_claim": "Customer reports the package was not delivered.",
"dispute_type": "not_delivered"
}'
Replace the following:
API_KEY: your test key, which starts with st_test_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
POST/v1/integrations/sandbox/tags/{id}/mock-journeyInject a mock Los Angeles to Dallas ping route into one of your sandbox tags.
Request, responses and example of POST /v1/integrations/sandbox/tags/{id}/mock-journey
Operation mock_journey
Sets the tag's origin (Los Angeles, Arcadia) and destination (Dallas) coordinates and injects pings along the route. stage sets how far the journey goes: started (3 pings), in_transit (8), approaching (13) or complete (all 15, the default). Send {} for the complete journey.
Parameters of mock_journey
Path parameters:
Parameters of mock_journey
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
200 Pings injected and origin and destination set; data is { tag_id, stage, inserted }
data: any
400 Malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
403 Not available in production, use sandbox-api.secretag.co (sandbox operations run only on the sandbox host)
404 Tag not found, or not assigned to your organization
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your test key, which starts with st_test_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
POST/v1/integrations/sandbox/tags/{id}/resetReset one of your sandbox tags.
Request, responses and example of POST /v1/integrations/sandbox/tags/{id}/reset
Operation reset_tag
Clears the tag's pings, recipient, addresses, order ID and metadata, deletes its linked shipment and packages, and sets its state to awaiting_first_ping. SecreTag also clears the declared value of the deleted shipment. No request body is needed. data is { tag_id, pings_deleted, shipment_deleted, state }.
Parameters of reset_tag
Path parameters:
Parameters of reset_tag
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
Responses of reset_tag
200 Tag reset
data: any
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
403 Not available in production, use sandbox-api.secretag.co (sandbox operations run only on the sandbox host)
404 Tag not found, or not assigned to your organization
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of reset_tag
curl -X POST "https://sandbox-api.secretag.co/v1/integrations/sandbox/tags/ID/reset" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your test key, which starts with st_test_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
POST/v1/integrations/sandbox/tags/{id}/risk-scoreEmit a risk.high_score event for one of your sandbox tags.
Request, responses and example of POST /v1/integrations/sandbox/tags/{id}/risk-score
Operation mock_risk_score
Raises a risk.high_score event for the tag; SecreTag relays it to your subscriptions like any other event. Send {} for a score of 85 with the factors route_deviation and dispute_history; score must be 0 to 100. No risk score record is stored. data is { tag_id, score, risk_factors, subscriptions_enqueued }, where subscriptions_enqueued is the tracking network's own count for SecreTag's relay (one subscription), not the number of your subscriptions.
Parameters of mock_risk_score
Path parameters:
Parameters of mock_risk_score
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
Risk factors to include in the webhook payload. Defaults to ["route_deviation", "dispute_history"].
score
integer (int32)
No
Risk score, 0 to 100. Defaults to 85 (the high-risk threshold).
Responses of mock_risk_score
200 risk.high_score event raised
data: any
400 Score must be between 0 and 100, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
403 Not available in production, use sandbox-api.secretag.co (sandbox operations run only on the sandbox host)
404 Tag not found, or not assigned to your organization
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your test key, which starts with st_test_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
POST/v1/integrations/sandbox/tags/{id}/stateForce one of your sandbox tags into a state.
Request, responses and example of POST /v1/integrations/sandbox/tags/{id}/state
Operation force_state
Sets the tag's lifecycle state directly, skipping the normal transitions. Valid state: awaiting_first_ping, at_origin, in_transit, approaching, delivered, delivery_verification, disputed_in_transit, completed. data is { tag_id, state }.
Parameters of force_state
Path parameters:
Parameters of force_state
Name
In
Type
Required
Description
id
path
string
Yes
The tag's printed ID (for example 0938NYH), BLE identifier or uuid. A tag not assigned to your organization answers 404.
One of: awaiting_first_ping, at_origin, in_transit, approaching, delivered, delivery_verification, disputed_in_transit, completed
Responses of force_state
200 State updated
data: any
400 Invalid state value, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
403 Not available in production, use sandbox-api.secretag.co (sandbox operations run only on the sandbox host)
404 Tag not found, or not assigned to your organization
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your test key, which starts with st_test_
ID: the tag's printed ID (for example 0938NYH), BLE identifier or uuid
POST/v1/integrations/sandbox/webhooks/testSend a sample event to your webhook subscriptions.
Request, responses and example of POST /v1/integrations/sandbox/webhooks/test
Operation test_webhook
SecreTag builds its own sample event of event_type for your organization (realistic sample objects carrying your organization_id, on your first assigned tag when you have one) and queues it to each of your active subscriptions that takes that event. subscriptions_enqueued is the number of your matching active subscriptions. The deliveries are signed and retried like real events and appear in list_webhook_deliveries. Nothing is sent to the tracking network. Event types: tag.state_changed, tag.delivered, tag.approaching, tag.carrier_updated, dispute.opened, dispute.resolved, dispute.evidence_submitted, shipment.created, shipment.delivered, risk.high_score.
string, one of tag.state_changed, tag.delivered, tag.approaching, tag.carrier_updated, dispute.opened, dispute.resolved, dispute.evidence_submitted, shipment.created, shipment.delivered, risk.high_score
Yes
One of the ten event types.
Responses of test_webhook
200 Sample event queued; data is { event_type, subscriptions_enqueued }
data: any
400 event_type missing or not one of the ten event types, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
403 Not available in production, use sandbox-api.secretag.co (sandbox operations run only on the sandbox host)
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
API_KEY: your test key, which starts with st_test_
Risk
Address risk scoring.
GET/v1/risk/address/{hash}Get a stored risk score by address hash.
Request, responses and example of GET /v1/risk/address/{hash}
Operation get_address_score
Answers 404 unless your organization assessed this address hash before, with assess_address or assess_batch. The score is the tracking network's one record for the address: created_at and updated_at are when the network first and last scored the address for any of its customers, and address_input is the input it keeps. The dispute-history signal of a score is computed by the tracking network over the history of every SecreTag customer.
Parameters of get_address_score
Path parameters:
Parameters of get_address_score
Name
In
Type
Required
Description
hash
path
string
Yes
Normalized address hash, as returned in address_hash
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
404 No score found for this address, or your organization has not assessed it
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
503 Upstream not configured
Example request of get_address_score
curl -X GET "https://api.secretag.co/v1/risk/address/HASH" \
-H "X-API-Key: API_KEY"
Replace the following:
API_KEY: your live key, which starts with st_live_
HASH: the normalized address hash, as returned in address_hash
POST/v1/risk/assessScore one delivery address.
Request, responses and example of POST /v1/risk/assess
Operation assess_address
Returns the address's risk score and its six signals; the address_hash is recorded for your organization, so get_address_score can read it later. The dispute-history signal of a score is computed by the tracking network over the history of every SecreTag customer.
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your live key, which starts with st_live_
POST/v1/risk/batchScore up to 100 addresses.
Request, responses and example of POST /v1/risk/batch
Operation assess_batch
addresses must hold 1 to 100 addresses; anything else answers 400 before anything is sent. cached counts the results whose address hash your organization had assessed before this call. The dispute-history signal of a score is computed by the tracking network over the history of every SecreTag customer.
400addresses must be an array of 1 to 100 addresses, an invalid address, or a malformed JSON body
401 Missing, unknown or revoked API key, or a key of the other environment (Invalid API key)
413 Request body too large (limit 1 MB)
429 Rate limit exceeded: more than 600 requests per minute for your organization, or more than 60 failed authentications per minute from your IP address
502 Upstream unavailable: the tracking network timed out, could not be reached or failed
API_KEY: your live key, which starts with st_live_
Schemas
AddressRiskScoreobject
The tracking network's one stored risk score for a normalized address: created_at and updated_at are when the network first and last scored the address for any of its customers, and address_input is the input it keeps.
ArchivedFilterstring, one of exclude, include, only
exclude (the default) hides archived tags. include (archived tags too) and only (archived tags only) are not yet verified against the tracking network.
Declares a value for the new shipment. Each rule refused answers 400: declared_value a decimal string with at most two decimals, greater than zero; currency equal to your organization's currency. null is refused on create.
master_tracking_number
string, nullable
No
order_id
string, nullable
No
origin_address
string, nullable
No
origin_lat
number (double), nullable
No
origin_lng
number (double), nullable
No
origin_location_id
string (uuid), nullable
No
Not supported by SecreTag: a request that names it answers 400.
Packages to create: each names a tag and an optional child tracking number.
recipient_email
string, nullable
No
recipient_name
string, nullable
No
recipient_phone
string, nullable
No
service_level
string, nullable
No
Service level (e.g., ground, express, priority, next_day, economy)
CreateWebhookSubscriptionRequestobject
Request to create a webhook subscription.
Fields of CreateWebhookSubscriptionRequest
Field
Type
Required
Description
event_types
array of string, one of tag.state_changed, tag.delivered, tag.approaching, tag.carrier_updated, dispute.opened, dispute.resolved, dispute.evidence_submitted, shipment.created, shipment.delivered, risk.high_score, nullable
No
The event types to receive; omit or null for every event.
label
string, nullable
No
target_url
string
Yes
An HTTPS URL on a public address.
CreateWebhookSubscriptionResponseobject
The subscription just created, with its signing secret (returned only here).
Fields of CreateWebhookSubscriptionResponse
Field
Type
Required
Description
created_at
string (date-time)
Yes
event_types
array of string, one of tag.state_changed, tag.delivered, tag.approaching, tag.carrier_updated, dispute.opened, dispute.resolved, dispute.evidence_submitted, shipment.created, shipment.delivered, risk.high_score, nullable
No
The event types the subscription takes; null for every event.
id
string (uuid)
Yes
is_active
boolean
Yes
label
string, nullable
No
organization_id
string (uuid)
Yes
secret
string, nullable
No
The signing secret, returned once in this response and never again. Verify each delivery's X-SecreTag-Signature: sha256=<hex HMAC-SHA256 of the raw body> with it.
Dispute counts and figures, computed by SecreTag for your organization (see dispute_stats).
Fields of DisputeStatsResponse
Field
Type
Required
Description
amount_at_risk
number (double)
Yes
The sum of the declared values of your insured shipments in an open or investigating dispute, a number with two decimals in your organization's currency.
avg_resolution_hours
number (double), nullable
No
Mean hours from open to resolution, two decimals; null when no dispute is resolved.
evidence_generated
integer (int64)
Yes
Your disputes for which SecreTag recorded a successful generate_evidence call.
investigating
integer (int64)
Yes
open
integer (int64)
Yes
resolved
integer (int64)
Yes
shopify_submitted
integer (int64)
Yes
Your disputes that carry a shopify_submitted_at.
total
integer (int64)
Yes
ErrorResponseobject
The envelope of every error answer: success false, data null, error a message.
Fields of ErrorResponse
Field
Type
Required
Description
data
null
Yes
error
string
Yes
success
boolean, one of false
Yes
EvidenceLocationProofEntryobject
A single BLE location report in the evidence package.
Fields of EvidenceLocationProofEntry
Field
Type
Required
Description
accuracy_m
number (double), nullable
No
lat
number (double)
Yes
lng
number (double)
Yes
source
string
Yes
Detection source. "network" = satellite/terrestrial network; "ble" = direct BLE.
status
string
Yes
Proximity to the destination. One of "at_destination", "approaching" (< 1 km), or "in_transit".
tag_id
string (uuid)
Yes
Tag that produced this ping. Use with tag_count to group pings by tag in multi-box shipments.
time
string (date-time)
Yes
ForceStateRequestobject
Force a tag to a specific state.
Fields of ForceStateRequest
Field
Type
Required
Description
state
string
Yes
One of: awaiting_first_ping, at_origin, in_transit, approaching, delivered, delivery_verification, disputed_in_transit, completed
GenerateEvidenceResponseobject
The result of generate_evidence.
Fields of GenerateEvidenceResponse
Field
Type
Required
Description
evidence_pdf_key
string
Yes
Where the tracking network stored the evidence PDF; download it with get_evidence_pdf.
generated_at
string
Yes
RFC 3339 timestamp of generation.
JourneyPointobject
Journey point for map display
Fields of JourneyPoint
Field
Type
Required
Description
accuracy_m
number (double), nullable
No
lat
number (double)
Yes
lng
number (double)
Yes
source
string
Yes
time
string (date-time)
Yes
JourneyStagestring, one of started, in_transit, approaching, complete
How far through the mock journey to populate.
Values:
started
in_transit
approaching
complete
LastPingobject
Summary of last ping for a tag
Fields of LastPing
Field
Type
Required
Description
lat
number (double)
Yes
lng
number (double)
Yes
rssi
integer (int32), nullable
No
Radio signal strength (dBm) of the gateway that heard this ping, when reported.
source
string
Yes
time
string (date-time)
Yes
MarkReadResponseobject
An alert marked read.
Fields of MarkReadResponse
Field
Type
Required
Description
id
string (uuid)
Yes
read_at
string (date-time)
Yes
MockAlertRequestobject
Fields of MockAlertRequest
Field
Type
Required
Description
alert_type
string
No
Alert type. Defaults to delivery. One of: geofence, delivery, dispute, system, package_separation, gps_carrier_mismatch
severity
string
No
Alert severity. Defaults to warning. One of: info, warning, critical
MockCarrierEventRequestobject
Fields of MockCarrierEventRequest
Field
Type
Required
Description
status
string
Yes
Carrier status. One of: in_transit, out_for_delivery, delivered, exception
MockDisputeRequestobject
Fields of MockDisputeRequest
Field
Type
Required
Description
customer_claim
string
No
Customer's claim text. Defaults to a generic message. Max 1000 characters.
dispute_type
string
No
Dispute type. Defaults to not_delivered. One of: not_delivered, damaged, wrong_location, other
The declared value SecreTag keeps for this shipment; null when none is declared. Present on every shipment SecreTag returns.
master_status
string, nullable
No
master_tracking_number
string, nullable
No
order_id
string, nullable
No
organization_id
string (uuid)
Yes
origin_address
string, nullable
No
origin_lat
number (double), nullable
No
origin_lng
number (double), nullable
No
origin_location_id
string (uuid), nullable
No
public_id
string
Yes
recipient_email
string, nullable
No
recipient_name
string, nullable
No
recipient_phone
string, nullable
No
service_level
string, nullable
No
updated_at
string (date-time)
Yes
ShipmentInsuranceobject
A declared value SecreTag keeps for a shipment.
Fields of ShipmentInsurance
Field
Type
Required
Description
currency
string
Yes
Three-letter currency code: your organization's currency.
declared_at
string (date-time)
Yes
When the value was declared.
declared_value
string
Yes
The declared value, a decimal string with two decimals.
ShipmentInsuranceRequestobject
A declared value for a shipment.
Fields of ShipmentInsuranceRequest
Field
Type
Required
Description
currency
string
Yes
Must equal your organization's currency.
declared_value
string
Yes
A decimal string with at most two decimals and at most 13 digits before the point, greater than zero. A JSON number is refused.
ShipmentListPageobject
One page of your shipments: items and pagination are always present. Each item is a Shipment with its insurance; whether items also carry packages is not yet verified.
Sets the declared value, replacing any earlier one. Each rule refused answers 400: declared_value a decimal string with at most two decimals, greater than zero; currency equal to your organization's currency. null clears it; omit it to leave it unchanged.
master_tracking_number
string, nullable
No
order_id
string, nullable
No
origin_address
string, nullable
No
origin_lat
number (double), nullable
No
origin_lng
number (double), nullable
No
recipient_email
string, nullable
No
recipient_name
string, nullable
No
recipient_phone
string, nullable
No
service_level
string, nullable
No
Service level (e.g., ground, express, priority, next_day, economy)
UpdateTagRequestobject
Request to update a tag
Fields of UpdateTagRequest
Field
Type
Required
Description
auto_off_after_delivery
boolean, nullable
No
Per-tag override of the deactivate-after-delivery setting: omit to leave it unchanged, null to inherit the organization default, true or false to force it.
destination_address
string, nullable
No
destination_lat
number (double), nullable
No
destination_lng
number (double), nullable
No
geofence_radius_m
integer (int32), nullable
No
metadata
object, nullable
No
network_coverage_months
integer (int32), nullable
No
Accepted and not acted on by this operation.
network_off_override_at
string (date-time), nullable
No
Accepted and not acted on by this operation.
order_id
string, nullable
No
origin_address
string, nullable
No
origin_lat
number (double), nullable
No
origin_lng
number (double), nullable
No
recipient_email
string, nullable
No
recipient_name
string, nullable
No
recipient_phone
string, nullable
No
WebhookDeliveryobject
One relay of one event to one of your subscriptions (SecreTag's delivery log).
Fields of WebhookDelivery
Field
Type
Required
Description
attempts
integer (int32)
Yes
created_at
string (date-time)
Yes
delivered_at
string (date-time), nullable
No
event_id
string
Yes
The event's id: the tracking network's event id, or test_<uuid> for a test_webhook sample event.
event_type
string
Yes
id
string (uuid)
Yes
last_attempt_at
string (date-time), nullable
No
last_error
string, nullable
No
last_response_body
string, nullable
No
last_status_code
integer (int32), nullable
No
max_attempts
integer (int32)
Yes
next_retry_at
string (date-time), nullable
No
organization_id
string (uuid)
Yes
payload
object
Yes
The event body SecreTag sent.
status
string
Yes
pending, delivered, failed (8 attempts without a 2xx) or cancelled (the subscription was deactivated first).
subscription_id
string (uuid)
Yes
WebhookDeliveryListPageobject
One page of a subscription's delivery log: items and pagination.