Skip to content
Subsido

Matching

Watchlists

An accountant with three thousand clients should not have to search. Put the companies on a watchlist once; they are matched at once, and re-evaluated whenever a measure changes, with an event for every match that appears, changes or goes.

Business and aboveWatchlists need the watchlists capability. Up to 50 watchlists per account; the companies across all of them are capped by plan (5,000 on Business, unlimited on Enterprise).

Create a watchlist

curl -X POST "https://api.subsido.be/v1/watchlists" \  -H "Authorization: Bearer sb_live_..." \  -H "Content-Type: application/json" \  -d '{"name": "Clients Gent", "language": "nl", "options": {"statuses": ["open", "continuous", "forthcoming"]}}'
PropertyMeaning
name1 to 120 characters.
optionsThe same match options as POST /v1/match: statuses, instrument_types, include_not_eligible, include_unrelated. Applied to every company on the list.
languagenl, fr or en (default): the language of stored labels and questions.

201 with the watchlist: { id, name, options, language, companies, matches, created_at, updated_at, last_evaluated_at }, where id is wl_…, companies counts the companies on it and matches the current matches that are not not_eligible.

RouteWhat it does
GET /v1/watchlistsEvery watchlist of the account, in one page.
GET /v1/watchlists/{id}One watchlist.
PATCH /v1/watchlists/{id}Change name, options or language; send only what changes.
DELETE /v1/watchlists/{id}Delete it, with its companies and their matches.
POST /v1/watchlists/{id}/companiesAdd or replace companies, and evaluate them now.
GET /v1/watchlists/{id}/companiesThe companies on it, paged with limit and cursor.
DELETE /v1/watchlists/{id}/companies/{reference}Remove one company (URL-encode the reference).
GET /v1/watchlists/{id}/matchesThe current matches.

Add companies

curl -X POST "https://api.subsido.be/v1/watchlists/wl_06f8r9t2b4c6d8e0f2g4h6j8km/companies" \  -H "Authorization: Bearer sb_live_..." \  -H "Content-Type: application/json" \  -d '{"companies": [        {"reference": "client-0042", "company": {"postcode": "9000", "employees": 12, "turnover_eur": 1500000, "legal_form": "bv", "nace": ["62.010"]}},        {"reference": "client-0043", "company": {"postcode": "98200", "legal_form": "eenmanszaak"}, "project": {"topics": ["energy_efficiency"]}}      ]}'
  • 1 to 1,000 companies per request. Each has your own reference (1 to 200 characters), and company and project take exactly the properties of a match request.
  • A reference already on the watchlist is replaced, and does not count again against the plan’s company cap.
  • A company with invalid facts, a duplicate or an empty reference is rejected on its own; the rest are accepted.
  • Every accepted company is evaluated before the call returns, against the same measures as /v1/match, and counts as one match evaluation. The request is refused as a whole with match_quota_exceeded when the accepted companies would take you past your allowance, and with plan_required when they would take the account past its company cap.
{
  "watchlist_id": "wl_06f8r9t2b4c6d8e0f2g4h6j8km",
  "added": 1,
  "replaced": 0,
  "rejected": [
    {
      "reference": "client-0043",
      "error": {
        "code": "invalid_body",
        "message": "company.postcode: company.postcode is not a Belgian postcode",
        "details": {
          "field": "company.postcode"
        }
      }
    }
  ],
  "matches": 7,
  "meta": {
    "request_id": "req_0192d3a4b5c67d8e9f0a1b2c3d4e5f63",
    "warnings": []
  }
}

matches counts the accepted companies’ matches that are not not_eligible. The second company was rejected for a five-digit postcode; the first was added and matched.

Read the matches

curl "https://api.subsido.be/v1/watchlists/wl_06f8r9t2b4c6d8e0f2g4h6j8km/matches?company=client-0042" \  -H "Authorization: Bearer sb_live_..."
ParameterMeaning
companyOne company’s reference. Without it, every company’s matches.
include_not_eligibleAlso the not_eligible ones, when the watchlist’s options keep them. Default false.
limitRows to return, 1 to 5,000 (default 500). This list does not page.

The answer is { data, meta, disclaimer }. Each row is { company_reference, subsidy_id, match_status, score, result, subsidy_version, first_matched_at, updated_at }, where result is the match exactly as /v1/match computes it (status, confidence, relevance, reasons, unknowns, estimate), without the measure summary: read the measure with GET /v1/subsidies/{id}. subsidy_version is the version it was evaluated against.

Re-evaluation and events

The worker re-evaluates a watchlist whenever a measure it could match or one of its companies has changed since its last evaluation (last_evaluated_at). Background re-evaluation is included in the plan and never counts as match evaluations. Every difference becomes an event:

EventWhen
match.createdA measure starts to match a company (including at the first evaluation, when the companies are added).
match.status_changedA match’s status changes, say from possibly_eligible to likely_eligible. previous_status says from what.
match.removedA measure no longer matches: it closed, its rules changed, or the company’s facts did.

Match events belong to the watchlist’s owner. They reach only that account’s webhooks (filter them with watchlists or event_types) and never appear in the public change feed.

{
  "id": "chg_06f8s2m4d2a9b1c7e3g5h8j0kn",
  "event": "match.created",
  "created_at": "2026-09-27T07:00:03+02:00",
  "data": {
    "subject": "match",
    "id": "wl_06f8r9t2b4c6d8e0f2g4h6j8km:client-0042:federal:investeringsaftrek",
    "version": null,
    "categories": [
      "match.created"
    ],
    "diff": {},
    "summary": {
      "watchlist_id": "wl_06f8r9t2b4c6d8e0f2g4h6j8km",
      "company_reference": "client-0042",
      "subsidy_id": "federal:investeringsaftrek",
      "match_status": "likely_eligible",
      "previous_status": null,
      "subsidy": {
        "title": {
          "nl": "Investeringsaftrek",
          "fr": "Déduction pour investissement",
          "en": "Investment deduction",
          "de": null
        },
        "status": "continuous",
        "instrument_type": "tax_deduction",
        "issuer": "FOD Financiën",
        "closes_at": null,
        "regions": [],
        "topics": [
          "investment",
          "digitalisation"
        ],
        "url": "https://financien.belgium.be/nl/ondernemingen/vennootschapsbelasting/belastingvoordelen/investeringsaftrek",
        "source_id": "curated_federal"
      }
    }
  }
}

What we keep

Facts, not people

A watchlist stores your reference for each company and the company and project facts you sent, and the current matches. No names, no addresses, no people: matching needs facts about a company, not who runs it. Use a reference that means something to you and nothing to anyone else. Everything is kept until you remove the company or delete the watchlist.