TradeProtectedCommodity Trade Compliance

Sanctions Screening API

One endpoint, four official lists

Bring 28,242 sanctions and export-control entries from US OFAC, the UN, the EU and China MOFCOM into your own ERP, risk or KYC systems. Send a name; get back whether it matched, which entries it matched, and a link to the official record you can open and verify.

28,242list entries
4official sources
Dailyrefreshed
4output formats

Who it is for

Why not build it yourself

Four sources, four formats: OFAC ships CSV, the UN ships XML, the EU has its own database, and China MOFCOM has no API at all — only announcement web pages.

And the lists move daily — our last OFAC refresh came back 97 entries lighter (delistings must be synced too, or you produce false positives).

That maintenance cost is ongoing, not one-off.

Three steps to integrate

1. Subscribe to the API plan and create a key

The API requires the API plan (US$19.9/mo, includes everything in membership).

Sign in, open the Membership tab to subscribe, then create a key under API keys. Keys look like tp_xxxxxxxx.

The plaintext key is shown only once, at creation — put it into your secret manager right away.

2. Send a request

curl -H "Authorization: Bearer tp_YOUR_KEY"   "https://tradeprotected.com/api/v1/screen?name=GAZPROM"

3. Read the response

{
  "matched": true,
  "count": 2,
  "rows": [
    {
      "source": "OFAC",
      "name": "GAZPROM NEFT",
      "type": "entity",
      "programs": "RUSSIA-EO14024",
      "listed_on": "2022-02-24",
      "url": "https://sanctionssearch.ofac.treas.gov/..."
    }
  ]
}

matched is a boolean you can branch on directly; rows[].url points at the official record — file it as your verification evidence.

Endpoints

GET/api/v1/screen

Screen a single name. Parameter name (required, max 200 characters). A 7-digit number is treated as a vessel IMO and matched exactly.

POST/api/v1/screen

Batch screening, up to 100 names per call. Handy for checking buyer, seller, shipowner and consignee in one go before an order.

GET/api/v1/sanctions

Browse or bulk-pull the lists, for keeping your own copy in sync. Parameters: q keyword, source, type, limit (default 100, max 500), offset.

GET/api/v1/sources

Entry counts and last-updated time per source. A sync job can check this first and skip a full pull when nothing changed.

Parameters

nameName to screen, or a 7-digit IMO. Required for GET /screen
namesArray of names for batch screening, in the POST body, max 100
sourceOFAC / UN / EU / EUX / CN; empty means all
typeentity / individual / vessel / aircraft
formatjson (default) / xlsx (Excel) / csv / ndjson
limitRows per page, default 100, max 500
offsetOffset, used with limit for paging

Three ways to use it

Same data, three ways to consume it, ordered by how much code you have to write:

Option 1: embed it in your own site

Paste the snippet below into any page of your corporate site and a sanctions search box appears, backed by our database and plain enough to blend into your layout. A good fit for forwarders, law firms and associations offering clients a self-service check.

<iframe src="https://tradeprotected.com/embed?key=tp_YOUR_KEY&lang=en"
        style="width:100%;height:420px;border:1px solid #e4eaf1;border-radius:12px"
        loading="lazy"></iframe>

Lock it to your domain

A key inside embed code is publicly visible — anyone viewing your page source can read it. So set the allowed domains for that key under Membership → API keys (e.g. yourcompany.com); even if the key is copied, it will not work on another site. This is the same approach front-end keys like Google Maps use.

We recommend separate keys for embedding and for server-side calls: lock the embed key to your domain, and keep the server key unlocked but only on your server. One account can hold five keys at a time, which is enough to split by environment.

Option 3: export to a spreadsheet

Add the format parameter — every query endpoint supports it.

# export the China MOFCOM list to Excel
curl -H "Authorization: Bearer tp_YOUR_KEY"   "https://tradeprotected.com/api/v1/sanctions?source=CN&limit=500&format=xlsx"   -o cn-list.xlsx

# save a single screening result as a spreadsheet for your audit file
curl -H "Authorization: Bearer tp_YOUR_KEY"   "https://tradeprotected.com/api/v1/screen?name=GAZPROM&format=xlsx"   -o gazprom.xlsx

# look up a vessel by IMO
curl -H "Authorization: Bearer tp_YOUR_KEY"   "https://tradeprotected.com/api/v1/screen?name=9209508"

Code samples

Python

import requests

KEY = "tp_YOUR_KEY"
r = requests.get(
    "https://tradeprotected.com/api/v1/screen",
    params={"name": "GAZPROM"},
    headers={"Authorization": "Bearer " + KEY},
    timeout=20,
)
r.raise_for_status()
data = r.json()

if data["matched"]:
    print("MATCH", data["count"], "hit(s) — needs manual review")
    for row in data["rows"]:
        print(row["source"], row["name"], row["url"])

Node.js

const KEY = process.env.TP_API_KEY;

async function screen(name) {
  const url = new URL("https://tradeprotected.com/api/v1/screen");
  url.searchParams.set("name", name);
  const r = await fetch(url, { headers: { authorization: "Bearer " + KEY } });
  if (!r.ok) throw new Error("screen failed: " + r.status);
  return r.json();
}

const out = await screen("SOVCOMFLOT");
console.log(out.matched ? "MATCH " + out.count : "clear");

Batch (Python)

names = ["GAZPROM", "ACSL", "SOVCOMFLOT"]
r = requests.post(
    "https://tradeprotected.com/api/v1/screen",
    json={"names": names},
    headers={"Authorization": "Bearer " + KEY},
    timeout=60,
)
for item in r.json()["results"]:
    flag = "MATCH" if item["matched"] else "clear"
    print(flag, item["query"], item["count"])

Quota and error codes

1000 calls per key per day, resetting at 00:00 UTC. Every response carries these two headers:

X-RateLimit-Limit: 1000
X-RateLimit-Remaining: 999

An account can hold up to five active keys. Splitting them by environment (production / staging / a specific colleague) means you can revoke one without disturbing the other callers.

Errors

Errors always return {"error":{"code":"...","message":"..."}}. Branch on code, not on the message text.

401missing_key no key supplied · invalid_key key invalid or revoked
403membership_required not subscribed or expired — keys stop working the moment the plan lapses and resume on renewal, no need to reissue
429quota_exceeded daily allowance used up
400missing_name / name_too_long / too_many_names parameter problems

Important

Matching is normalised substring and phrase matching, so a hit is a due-diligence signal, not a legal conclusion. Namesakes and transliteration differences can produce false positives and false negatives; make the final call against the official record at url.

The API plan includes everything in membership, plus the data API, the embeddable widget and Excel export.

Comparable screening APIs are typically annual contracts starting in the thousands of dollars. Ours is monthly and cancellable any time. Run a few queries free and judge the data before committing.

Try it free

Need more than 1000 calls a day, a dedicated quota or on-premise deployment? See enterprise plans →

Other languages: 中文 · Русский · Español · 日本語 · 한국어 · العربية