Sanctions Screening — OFAC SDN & EU List Name Check (KYC/AML)
Pricing
from $2.10 / 1,000 result items
Sanctions Screening — OFAC SDN & EU List Name Check (KYC/AML)
Screen names of people, companies and vessels against the US OFAC SDN list and the EU consolidated sanctions list. Fuzzy matching with score, aliases, program, country, listing date. Bulk screening. Built for compliance agents. No API key.
Pricing
from $2.10 / 1,000 result items
Rating
0.0
(0)
Developer
Samat Makatov
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
3 days ago
Last modified
Categories
Share
Screen people, companies, vessels and aircraft against the US OFAC SDN and Consolidated (non-SDN) lists, the EU Consolidated Financial Sanctions List, the UN Security Council Consolidated List and the UK Sanctions List (FCDO) in one run. Names are transliterated (Cyrillic → Latin), stripped of legal forms and matched with five explainable similarity methods; every hit tells you which listed name matched, how and with what score. Built for KYC/AML onboarding, counterparty due diligence and agent workflows.
No API key, no proxy, no browser. Lists are downloaded live from the official publishers on every run. Made by Yadroo.
A list that cannot be downloaded fails the run. If a publisher's download is down — the EU file was unreachable for about a day on 1–2 October 2026 — the run stops with that reason and charges no rows, instead of returning "clear" verdicts that never checked that list. Turn on
allowPartialto screen the other lists instead; every row then says which lists it covers (complete,listsScreened,listsFailed).
Use cases
- Customer / supplier onboarding — batch-screen a list of counterparties, get one row per name with
riskLevel(outputMode=summary) for an analyst queue. - Payment pre-check — screen the beneficiary and the bank (
entitieswithtypeandcountry) against OFAC + EU + UN + UK before releasing a wire. - Periodic re-screening — schedule the actor weekly on your client book; compare
hitCountwith the previous run to catch new designations. - Russia / Iran exposure review — restrict to
programs: ["RUSSIA-EO14024", "UKR", "Russia"]andcountries: ["russia"]to focus on one regime. - Vessel & aircraft checks —
entityTypes: ["vessel", "aircraft"]for shipping, chartering and trade-finance desks. - Agent tool — call via MCP from an LLM agent to answer "is X sanctioned, by whom, since when?" with a citable source URL.
Input
| Field | Type | Default | Notes |
|---|---|---|---|
names | string[] | — | Names to screen (people, companies, vessels). Cyrillic and diacritics are fine. Max 5,000 names per run in total; see Limits for how many fit in one run. |
entities | object[] | — | Structured alternative: { "name", "type", "country", "ref" }. type narrows to individual/entity/vessel/aircraft (also person, company, ship, plane); an unknown type stops the run with an error instead of screening against every type. country keeps only entries linked to that country; ref (your customer id) is echoed back in the output. Can be combined with names. |
lists | string[] | ["ofac", "eu", "un"] | Any of ofac_sdn, ofac_consolidated, eu, un, uk. Groups: ofac = SDN + Consolidated, all = all five. Other spellings: sdn, non-sdn, ofsi/hmt/fcdo = uk. uk (the FCDO UK Sanctions List) is the largest download, so add it when you need UK coverage. Letter case does not matter; an unknown name stops the run with the valid ones. |
minScore | text, 0.5–1 | "0.85" | Similarity threshold. 1 = exact only (after normalization), 0.95 = typo-tolerant, 0.85 = wide net for manual review. Values outside 0.5–1 are read as the nearest bound and the status says so. Below ~0.8 far more listed names have to be scored, so runs are slower. |
entityTypes | string[] | — | Keep only these listed types: individual, entity, vessel, aircraft, unknown. |
programs | string[] | — | Case-insensitive substring filter on the program / regime code (see Reference). ["RUSSIA"] matches RUSSIA-EO14024, CAATSA - RUSSIA, Russia… |
countries | string[] | — | Substring filter on countries linked to the entry (nationality, address, vessel flag). |
includeAliases | boolean | true | Match against a.k.a. / f.k.a. names too (recommended — most hits on transliterated names come from aliases). |
strictTokenMatch | boolean | false | Disable the token-containment method, so a short query such as "Rosneft" no longer matches "OPEN JOINT-STOCK COMPANY ROSNEFT OIL COMPANY". |
allowPartial | boolean | false | Off: a requested list that cannot be downloaded fails the run with the reason, and no rows are charged — a "clear" must never cover a list nobody checked. On: the run screens the lists that loaded; every row has complete: false and listsFailed, a summary row without a match gets riskLevel: "incomplete" instead of clear, and the status starts with INCOMPLETE. |
maxHitsPerName | integer 1–100 | 10 | Cap on hits per screened name. The best hit of every list that matched is kept first — full-blocking lists (OFAC SDN, UN, EU, UK) before OFAC non-SDN — so a cap never hides an SDN designation behind weaker hits; the remaining places go to the highest scores. Equal scores are ordered OFAC SDN → UN → EU → UK → OFAC consolidated. |
outputMode | hits | summary | hits | hits: one row per (name × hit). summary: one row per screened name with riskLevel, hitCount and nested top hits. |
includeClear | boolean | true | Emit a row (matched: false) for names with no hit so the dataset covers the whole batch. |
fields | string[] | all | Keep only these output columns, in this order. query, matched and complete are always included. Names depend on outputMode (see Output); letter case is corrected, an unknown name stops the run with a suggestion. |
outputMode and entityTypes are fixed lists: Apify refuses any other value before the run starts (no run, no charge).
Reference
Lists
| key | Publisher / list | Entries (Oct 2026) | Status |
|---|---|---|---|
ofac_sdn | US Treasury OFAC — Specially Designated Nationals (SDN.CSV + ALT + ADD) | ~19,500 | downloaded on every run |
ofac_consolidated | OFAC Consolidated non-SDN (SSI, NS-PLC, CMIC, FSE, CAPTA…) | ~480 | downloaded on every run |
eu | EU Consolidated Financial Sanctions List (FSF CSV 1.1) | ~6,200 | downloaded on every run |
un | UN Security Council Consolidated List (XML) | ~1,000 | downloaded on every run |
uk | UK Sanctions List published by the FCDO (XML from sanctionslist.fcdo.gov.uk; the address is read from the gov.uk publication on every run). It replaced OFSI's Consolidated List, which closed on 28 January 2026. | ~6,400 | downloaded on every run |
OFAC program codes (most frequent; 73 codes in total)
RUSSIA-EO14024, SDGT, IFSR, SDNTK, NPWMD, IRAN-EO13902, GLOMAG, ILLICIT-DRUGS-EO14059, IRAN, UKRAINE-EO13662, IRAN-EO13846, TCO, IRGC, CYBER2, IRAN-HR, UKRAINE-EO13661, DPRK4, BELARUS-EO14038, VENEZUELA-EO13850, PAARSSR-EO13894, VENEZUELA, BALKANS, DPRK3, IRAQ2, UKRAINE-EO13660, BURMA-EO14014, SDNT, DPRK2, IRAN-EO13876, ELECTION-EO13848, FTO, UKRAINE-EO13685, DRCONGO, CYBER4, CUBA-EO14404, CAATSA - RUSSIA, NICARAGUA, CUBA, BELARUS, DPRK, VENEZUELA-EO13884, MAGNIT, SUDAN-EO14098, LIBYA3, IRAN-EO13871, IRAN-CON-ARMS-EO, IRAN-TRA, SOMALIA, CAR, PEESA-EO14039, IFCA, SOUTH SUDAN, BALKANS-EO14033, CAATSA - IRAN, HOSTAGES-EO14078, LIBYA2, ICC-EO14203, HRIT-IR, LEBANON, IRAQ3, YEMEN, CYBER3, RUSSIA-EO14065, NICARAGUA-NHRAA, DARFUR, ETHIOPIA-EO14046, MALI-EO13882, NS-PLC, PAIPA, SSIDES, DPRK-NKSPEA, HRIT-SY, UHRPA. Consolidated-only codes: CMIC-EO13959, HKAA, 561-Related. Full descriptions: OFAC program tag definitions.
EU programme codes (34)
UKR (Ukraine territorial integrity / Russia), IRN, SYR, BLR, TAQA (ISIL/Al-Qaida), PRK, HR (global human rights), AFG, MMR, COD, RUSDA (Russia destabilising activities), IRQ, RUS, VEN, LBY, TERR, CHEM, MDA, TUN, CYB, SDNZ, SOM, NIC, EUAQ, CAF, HAM, HTI, YEM, SDN, SSD, GTM, UNLI, GIN, MLI. Regime pages: sanctionsmap.eu.
UK regimes
The UK Sanctions List names each regime by its regulations, e.g. The Russia (Sanctions) (EU Exit) Regulations 2019, The Iran (Sanctions) (Nuclear) (EU Exit) Regulations 2019, The Global Human Rights Sanctions Regulations 2020, The Cyber (Sanctions) (EU Exit) Regulations 2020. The programs filter is a case-insensitive substring match, so ["Russia"] keeps these UK entries together with OFAC RUSSIA-EO14024 and similar; ["Global Human Rights"], ["Cyber"], ["Iran"] work the same way. UN list types use committee codes (Al-Qaida, DPRK, Iran, Libya, Taliban, DRC, Somalia, Yemen, CAR, South Sudan, Mali, Haiti, Sudan, Iraq).
Matching methods (method field)
| method | meaning | score |
|---|---|---|
exact | identical after normalization (lower-case, transliteration, diacritics and legal forms removed) | 1.0 |
token_sort | same words in a different order ("Putin Vladimir" ↔ "Vladimir Putin") | 0.98 |
compact | same letters, different spacing or hyphens ("Gazprom Bank" ↔ "GAZPROMBANK") | 0.97 |
token | all query words are contained in the listed name ("Rosneft" ⊂ "…ROSNEFT OIL COMPANY"), or all words of the listed name are in the query ("Sberbank of Russia" ⊃ "Сбербанк") — scored by how much of the longer name they cover | 0.75–0.97 |
dice | character-bigram similarity, robust to spelling variants | 0–1 |
jaro_winkler | typo tolerance for short personal names | 0–0.97 |
Normalization removes ~80 legal-form tokens (LLC, LTD, JSC, OOO, AO, GmbH, S.A., PJSC, TOO, LLP…), so "Gazprombank" and "GAZPROMBANK JOINT STOCK COMPANY" are an exact match.
Every hit carries matchReason — a plain-English explanation of the score, e.g. all query words found in "sberbank russia" (they cover 57% of it) or similar spelling "acme" vs "ace" (Jaro-Winkler 0.905); lowered to 0.662: short name (3 letters), length ratio 0.75.
Speed does not change the result: an index rules out listed names that cannot reach minScore (no shared word, too few shared letters or letter pairs) and scores the rest exactly as a full comparison would — the unit tests compare the two on thousands of name pairs at every threshold.
Guardrails against false positives
Character metrics are optimistic on short strings, shared prefixes and shared generic words. These rules can only lower a score, and each one is named in matchReason:
| Rule | Example it stops | Effect |
|---|---|---|
| Short name — fuzzy match where the shorter name has < 5 letters | "Acme Trading LLC" → acme vs vessel "ACE" (was 0.905); "Tesla" vs "TESA" | capped at 0.75 |
| Length ratio — shorter/longer (spaces ignored) below 0.85 | "Globex Corporation" vs "GLOBEXBANK" (was 0.892) | score × ratio / 0.85 |
| Weakest word — every distinctive query word needs a close counterpart (Jaro-Winkler bounded by edit distance) | "Kaspi Bank" vs "EKSI BANK", "Yevgeny Prigozhin" vs "Yevgeny Primakov" | capped at that word's similarity |
| Generic words — "bank", "air", "oil", "trading", "electronics", "industries"… (≈100 words) do not make two names similar and cost little when missing | "Air Astana" vs "AIR ALANNA", "Samsung Electronics" vs "Sanam Electronics" | ignored in the word check, weight 0.6 in coverage |
| Numbers must match | vessel "Adrian Darya 2" vs "ADRIAN DARYA 1"; "Grace 1" vs "MARIA GRACE" | capped at 0.8 |
| One word that is only a secondary word of the other name | "Apple Inc" vs "ORIENTAL APPLE COMPANY" | 0.8 |
| One 5–7-letter word contained in a longer name | "Globex" vs "GLOBEX COMMERCIAL BANK" 0.84; "Rosneft" vs "ROSNEFT OIL" 0.93 | 0.75 + 0.22 × coverage (long words such as "Sberbank" keep 0.85 + 0.12 × coverage) |
| Listed name shorter than the query | "Northern Lights Shipping" vs "NORTHERN SHIPPING" | at most 0.9 (low risk) |
Checked against the full OFAC/EU/UN/UK lists: real names and variants still match (Gazprombank / Gazprom Bank / Газпромбанк, Sberbank / Sberbank of Russia / Сбербанк, Rosneft / Роснефть, VTB, Alfa-Bank, Sovcombank / Sovkombank, Promsvyazbank / Promsviazbank, Bank Otkritie / Otkrytie Bank, Putin, Rotenberg, Prigozhin, Kadyrov, vessels ADRIAN DARYA 1, NS CHAMPION, SCF PRIMORYE), while fictional or unrelated names (Acme Trading, Globex, Initech, Tesla, Amazon, Kaspi Bank, Halyk Bank, Air Astana, Maersk, Nestle) come back clear at the default 0.85.
Examples
Onboarding batch — one verdict per name
{ "names": ["Gazprombank", "Acme Trading LLC", "Rosneft", "Maria Ivanova"], "outputMode": "summary", "minScore": "0.9" }
Wire pre-check with typed entities and customer refs, all five lists
{"entities": [{ "name": "Sberbank", "type": "company", "country": "Russia", "ref": "bene-bank" },{ "name": "Ivan Petrov", "type": "person", "ref": "bene-1" }],"lists": ["all"], "minScore": "0.92", "maxHitsPerName": 5}
Russia-regime exposure only
{ "names": ["Alfa-Bank", "Novatek", "Lukoil"], "lists": ["ofac", "eu", "uk"], "programs": ["RUSSIA", "UKR", "CAATSA"], "outputMode": "summary" }
Vessel screening (shipping / trade finance)
{ "names": ["MAR AZUL", "Pegas", "Sea Dragon"], "entityTypes": ["vessel"], "lists": ["ofac_sdn", "uk", "eu"], "minScore": "0.9" }
Strict mode for automated blocking (few false positives), only the columns you need
{ "names": ["Apple Inc", "John Smith"], "minScore": "0.97", "strictTokenMatch": true, "fields": ["score", "list", "name", "url"] }
Screen whatever is reachable when a publisher is down (rows say what was covered)
{ "names": ["Gazprombank"], "lists": ["all"], "allowPartial": true, "outputMode": "summary" }
Output
outputMode=hits — one item per (screened name × hit):
{"query": "Gazprombank", "queryRef": null, "queryType": null, "queryCountry": null, "queryIndex": 1,"matched": true, "score": 1, "method": "exact","matchReason": "identical after normalization (\"gazprombank\")","matchedName": "GAZPROMBANK JOINT STOCK COMPANY", "matchedOn": "name", "commonTokens": ["gazprombank"],"list": "ofac_sdn", "listLabel": "OFAC SDN (US Treasury Specially Designated Nationals)","id": "17016", "name": "GAZPROMBANK JOINT STOCK COMPANY", "type": "entity","programs": ["UKRAINE-EO13662", "RUSSIA-EO14024"], "program": "UKRAINE-EO13662; RUSSIA-EO14024","countries": ["Russia", "Mongolia", "Kazakhstan", "India", "China"], "country": "Russia; Mongolia; Kazakhstan; India; China","aliases": ["GAZPROMBANK OPEN JOINT STOCK COMPANY", "BANK GPB JSC", "JOINT STOCK BANK OF THE GAS INDUSTRY GAZPROMBANK"], "listedOn": null,"remarks": "SWIFT/BIC GAZPRUMM; Website www.gazprombank.ru; ...","url": "https://sanctionssearch.ofac.treas.gov/Details.aspx?id=17016","listsRequested": ["ofac_sdn", "ofac_consolidated", "eu", "un"], "listsScreened": ["ofac_sdn", "ofac_consolidated", "eu", "un"],"listsFailed": [], "complete": true,"screenedAt": "2026-10-02T07:57:00.000Z"}
| Field | Description |
|---|---|
query, queryRef, queryType, queryCountry | What you asked for (echoed, including your ref). |
queryIndex | 1-based position of the name among the screened names (names first, then entities); tells repeated names apart. |
matched | false on the "clear" row (includeClear). |
score, method, matchReason, matchedName, matchedOn, commonTokens | Match explanation: score 0–1, which method fired, why (including any guardrail that lowered the score), which listed name (primary or alias) matched, shared words. |
list, listLabel | Source list key and human label. On clear rows: every list actually screened (ofac_sdn+ofac_consolidated+eu+un). |
id, name, type | Publisher's id (OFAC uid, EU logical id, UN DATAID, UK Sanctions List unique id), primary name, individual/entity/vessel/aircraft/unknown. |
programs / program | Regime codes as array and joined string. |
countries / country | Countries linked to the entry (nationality, address, vessel flag). |
aliases | Up to 20 a.k.a. names. |
listedOn | Designation date (ISO) when the list provides it. |
remarks | Publisher's remarks / identifiers, trimmed to 500 chars. |
url | Source page for the entry (OFAC detail page; list home for EU/UN/UK). |
listsRequested, listsScreened, listsFailed, complete | Which lists the verdict covers. complete is true when every requested list was screened; it is false only with allowPartial when a list could not be downloaded (listsFailed names it). |
screenedAt | ISO timestamp of the screening. |
outputMode=summary — one item per name: query, queryRef, queryType, queryCountry, queryIndex, matched, hitCount, hitsOmitted (further matches above minScore left out by maxHitsPerName), topScore, riskLevel (high ≥ 0.97 / medium ≥ 0.9 / low below / clear = no match on a complete screen / incomplete = no match, but a requested list was not screened), listsRequested, listsScreened, listsFailed, complete, listsHit, hits[] (score, method, matchReason, matchedName, matchedOn, list, id, name, type, programs, countries, listedOn, url), screenedAt.
Each run also writes a SUMMARY record to its key-value store (linked from the run's output): names requested and screened, flagged and clear counts, lists requested / screened / failed (with the reason), entries per list, rows delivered, and why the run stopped if it stopped early. The run's status message says the same in one line.
Use it from code / agents
curl -X POST "https://api.apify.com/v2/acts/yadroo~sanctions-screen/run-sync-get-dataset-items?token=$APIFY_TOKEN" \-H "Content-Type: application/json" \-d '{"names":["Gazprombank","Acme Trading LLC"],"outputMode":"summary"}'
run-sync endpoints answer only for runs under 300 seconds (about 1,000 names at the default memory); for bigger batches start the run asynchronously (as below) and read the dataset when it finishes.
import { ApifyClient } from 'apify-client';const client = new ApifyClient({ token: process.env.APIFY_TOKEN });const run = await client.actor('yadroo/sanctions-screen').call({ names: ['Gazprombank'], lists: ['all'] });const { items } = await client.dataset(run.defaultDatasetId).listItems();
from apify_client import ApifyClientclient = ApifyClient(os.environ["APIFY_TOKEN"])run = client.actor("yadroo/sanctions-screen").call(run_input={"names": ["Gazprombank"], "outputMode": "summary"})items = client.dataset(run["defaultDatasetId"]).list_items().items
MCP: add https://mcp.apify.com to your agent and call the yadroo/sanctions-screen tool with the same JSON input.
Pricing
Pay per event: $0.001 per run start + $0.003 per dataset item. In summary mode one item = one screened name, so a 100-name batch ≈ $0.301; in hits mode heavy hitters produce up to maxHitsPerName rows each. List downloads are free. The row price follows your Apify plan (Bronze −10 %, Silver −20 %, Gold and above −30 %); the start event is the same on every plan, and platform usage is included.
Your maximum cost per run is respected: the run stops when it would exceed it and says so ("Stopped at your spending limit: N rows delivered"), naming the last screened name and how many of its rows were delivered. A run that fails because a list could not be downloaded charges only the start event.
Limits & FAQ
- Freshness — lists are downloaded from the publishers at run start (no cache);
screenedAtis on every row. - How many names per run — measured at the default 256 MB: downloading all five lists and indexing their ~93,000 names takes about 10 seconds when Apify's servers are quiet and up to about a minute when they are busy; each name then takes about 0.2 s at the default
minScore0.85 (600 names against all five lists: 138 s for the whole run). That is roughly 3,000 names in the default 15-minute run; lower thresholds are slower (below ~0.8 far more listed names have to be scored). More memory means more CPU: give the run 1 GB or more for big batches, or split them. A run that reaches its timeout stops cleanly, keeps every row it saved and says how many names it screened ("Stopped before the run timeout … Screened N of M names"). - Coverage — OFAC SDN + Consolidated, EU, UN, UK. Not included: national lists of other countries, PEP databases, adverse media. Use the
urlto verify a hit on the publisher's site before acting. - A list that cannot be downloaded — the run fails with the list and the reason, and charges no rows: a "clear" verdict must never cover a list that was not checked. With
allowPartialthe run screens the other lists instead and every row says which lists it covers (complete,listsScreened,listsFailed). - False positives — guardrails (above) stop short-name, shared-suffix and secondary-word matches, but common personal names ("John Smith") still match at 0.85 — that is what a wide net is for. For automated decisions use
minScore≥ 0.95 andstrictTokenMatch; keep 0.85 for human review and readmatchReason. - What the guardrails cost — subsidiaries whose name only shares a spelling-similar stem with the query ("Gazprombank" vs "GAZPROM NEFT", "Usama bin Ladin" vs "USAMA BIN LADEN NETWORK") now score below 0.85; lower
minScoreto ~0.8 if you want such related entities in the review queue. - Non-Latin input — Cyrillic (incl. Kazakh/Ukrainian letters) is transliterated; other scripts are matched against the lists' own non-Latin aliases only.
- Roadmap — UN/UK per-entry deep links, birth-date and passport matching for individuals, diff mode against the previous run.
Made by Yadroo. Related actors: domain-intel, ip-intel, wallet-intel, sec-edgar-filings, github-repo-intel.