SweKit - Swedish validators

Personnummer, orgnr, bankgiro, OCR, tài khoản sang IBAN và ngày ngân hàng của Thụy Điển dưới dạng máy chủ MCP từ xa chỉ đọc.

Máy chủ MCP được lưu trữ

npx add-mcp 'https://swekit-api.zenith-ops.workers.dev/mcp'

Cài vào Claude Code, Codex, Cursor và nhiều công cụ khác

Tài liệu

Conventions

  • Validators return {"valid": bool, "errors": [codes]} plus parsed fields. HTTP 200 even if the number is invalid; HTTP 400 only for missing/malformed parameters.
  • Errors: {"error":{"code","message"}}. Rate limit: HTTP 429 with Retry-After.
  • Response header X-Plan: free | pro | gateway.
  • POST example: curl -X POST https://swekit-api.zenith-ops.workers.dev/v1/personnummer -H 'content-type: application/json' -d '{"value":"811218-9876"}'

Access & limits

Anonymous demo: 20 requests/min/IP. Higher limits: send X-API-Key: <license key> (600 req/min). Marketplace subscribers use the marketplace's own key and quota. Pro key: contact the operator; pricing is not published.

curl examples

curl "https://swekit-api.zenith-ops.workers.dev/v1/personnummer?value=811218-9876"
curl -X POST "https://swekit-api.zenith-ops.workers.dev/v1/personnummer" -H 'content-type: application/json' -d '{"value":"811218-9876"}'
curl -H 'X-API-Key: YOUR_KEY' "https://swekit-api.zenith-ops.workers.dev/v1/account?clearing=7507&account=1211203"
# error response (missing parameter)
curl "https://swekit-api.zenith-ops.workers.dev/v1/orgnr"
{"error":{"code":"missing_parameter","message":"Missing parameter: value"}}

Error codes

HTTPCodeMeaning
400missing_parameterRequired input was not supplied
400bad_baseOCR base is invalid
400bad_yearYear must be 1900–2200
400bad_dateDate must be YYYY-MM-DD
400bad_inputBusiness-day input is invalid or out of range
400invalid_jsonPOST body is not valid JSON
401invalid_api_keyAPI key is invalid or expired
429rate_limitedPer-minute quota exceeded
500internal_errorUnexpected server error

MCP client configuration

Claude Desktop (claude_desktop_config.json):

{"mcpServers":{"swekit":{"command":"npx","args":["mcp-remote","https://swekit-api.zenith-ops.workers.dev/mcp"]}}}

Cursor:

{"mcpServers":{"swekit":{"url":"https://swekit-api.zenith-ops.workers.dev/mcp"}}}

VS Code (.vscode/mcp.json):

{"servers":{"swekit":{"type":"http","url":"https://swekit-api.zenith-ops.workers.dev/mcp"}}}

MCP server

Remote MCP endpoint https://swekit-api.zenith-ops.workers.dev/mcp (POST JSON-RPC 2.0: initialize, tools/list, tools/call). Tools: validate_personnummer, validate_orgnr, validate_bankgiro, validate_plusgiro, validate_ocr, generate_ocr, swedish_account_to_iban, validate_iban, lookup_clearing_number, swedish_holidays, swedish_date_info, add_business_days, count_business_days.

Semantics worth knowing

  • Bank accounts: checksum rules per Bankgirot (type 1 variants 1-2 mod-11; type 2 variants 1/3 mod-10, 2/4 mod-11). Swedbank 8xxx accounts are mod-10 "as a rule" and require the 5th clearing digit for IBAN. Plusgiro cannot be converted to IBAN. Some old accounts do not pass checksums.
  • Business days (bank mode): Saturdays, Sundays, public holidays plus midsommarafton, julafton and nyårsafton are not business days (these are equated with Sundays for payment deadlines under Swedish law). Use mode=work for plain weekday-minus-red-day logic. Check your own contracts for company-specific rules.
  • Personnummer: age and century are inferred from the separator (+ = 100+). Gender is from the 9th digit (registered legal sex). Use for validation, not identification.

FAQ

Does a valid number prove an account or person exists?

No. The API checks syntax, dates and checksums only; it is not an identity, ownership or account-existence service.

Are requests stored?

No request data is stored by the service. Use POST for personal numbers so they do not appear in URLs or access logs.

Can I convert Plusgiro to IBAN?

No. Swedish bank accounts can be converted when their clearing range is known; Plusgiro is not a bank account format.

What are the limits?

Anonymous access is 20 requests/minute/IP. A valid Pro key allows 600 requests/minute/key. Pro key: contact the operator; pricing is not published.

Endpoints

GET /v1/personnummer

Validate & parse a Swedish personnummer / samordningsnummer

valuestringPersonnummer in any common format (YYMMDD-NNNC, YYYYMMDDNNNC, with + for 100+). Prefer POST JSON {"value": "..."} so the number never appears in a URL.
curl "https://swekit-api.zenith-ops.workers.dev/v1/personnummer?value=811218-9876&at=2026-10-16"

GET /v1/orgnr

Validate organisationsnummer, derive legal form and Swedish VAT number (SE#########01)

valuestringOrg no. like 556036-0793, 5560360793, SE556036079301
curl "https://swekit-api.zenith-ops.workers.dev/v1/orgnr?value=556036-0793"

GET /v1/bankgiro

Validate bankgiro number (Luhn) and format it

valuestring7-8 digits, with or without dash
curl "https://swekit-api.zenith-ops.workers.dev/v1/bankgiro?value=5402-9681"

GET /v1/plusgiro

Validate plusgiro number

valuestring2-8 digits
curl "https://swekit-api.zenith-ops.workers.dev/v1/plusgiro?value=4-8"

GET /v1/ocr/validate

Validate an OCR / payment reference (Luhn check digit, optional length digit)

valuestringOCR digits
curl "https://swekit-api.zenith-ops.workers.dev/v1/ocr/validate?value=12351"

GET /v1/ocr/generate

Generate an OCR reference from a base number

basestringDigits, e.g. invoice number
length_digitbooleanAdd length digit (default false)
curl "https://swekit-api.zenith-ops.workers.dev/v1/ocr/generate?base=123&length_digit=true"

GET /v1/account

Validate a Swedish bank account (clearing + account, per Bankgirot rules) and convert to IBAN

numberstringFull account digits (clearing first), OR
clearingstringClearing number (4 digits; 5 for Swedbank 8xxx)
accountstringAccount number without clearing
curl "https://swekit-api.zenith-ops.workers.dev/v1/account?clearing=7507&account=1211203"

GET /v1/iban

Validate any IBAN (ISO 13616 mod-97, country length) and identify Swedish banks

valuestringIBAN, spaces allowed
curl "https://swekit-api.zenith-ops.workers.dev/v1/iban?value=SE45 5000 0000 0583 9825 7466"

GET /v1/bic

Validate BIC/SWIFT format

valuestring8 or 11 characters
curl "https://swekit-api.zenith-ops.workers.dev/v1/bic?value=ESSESESS"

GET /v1/clearing

Look up bank, BIC, IBAN id and account type for a clearing number

valuestringFirst 4 digits of the account number
curl "https://swekit-api.zenith-ops.workers.dev/v1/clearing?value=8327"

GET /v1/holidays

Swedish public holidays and eves for a year

yearinteger1900-2200 (default: current year)
curl "https://swekit-api.zenith-ops.workers.dev/v1/holidays?year=2026"

GET /v1/date

Info about a date: weekday (sv/en), ISO week, holiday names, business-day status

datestringYYYY-MM-DD
modestring"bank" (default; midsommarafton, julafton, nyårsafton also excluded) or "work"
curl "https://swekit-api.zenith-ops.workers.dev/v1/date?date=2026-12-24"

GET /v1/business-days/add

Add (or subtract) N business days to a date

datestringYYYY-MM-DD
daysintegerPositive or negative, |n| <= 3650
modestringbank (default) or work
curl "https://swekit-api.zenith-ops.workers.dev/v1/business-days/add?date=2026-12-22&days=2"

GET /v1/business-days/between

Count business days between two dates

fromstringYYYY-MM-DD
tostringYYYY-MM-DD
modestringbank (default) or work
curl "https://swekit-api.zenith-ops.workers.dev/v1/business-days/between?from=2026-10-16&to=2026-11-16"

Data sources

  • Bankgirot, Bankernas kontonummer, 2024-02-22.
  • Bankinfrastruktur i Sverige AB, IBAN and Swedish national account number page (clearing table, data date 2026-10-16).
  • Holidays: computed (Meeus/Jones/Butcher Easter algorithm + statutory rules).