Terug naar homepage

API & Webhooks

Haal je transfers en statistieken programmatisch op, en ontvang een melding zodra iemand je bestanden downloadt. Read-only REST + HMAC-gesigneerde webhooks.

1. Aan de slag

Maak een API-sleutel aan op je accountpagina (onderdeel van elk betaald plan). De sleutel wordt één keer getoond — bewaar 'm veilig. Stuur 'm mee in elke aanvraag:

Authorization: Bearer dlk_live_xxxxxxxxxxxxxxxxxxxx

2. Endpoints

Basis-URL: https://downloadlink.nl/api/v1. Alle responses zijn JSON en beperkt tot je eigen account.

GET /api/v1/me

Account + opslagverbruik.

curl -H "Authorization: Bearer dlk_live_xxx" \
     https://downloadlink.nl/api/v1/me

{
  "email": "jij@bedrijf.nl",
  "is_trial": false,
  "plan": "100 GB",
  "storage": { "used_bytes": 5242880, "quota_bytes": 107374182400, "percent": 0 }
}

GET /api/v1/transfers

Je transfers (nieuwste eerst). Parameter ?limit= (1–200, standaard 50).

{
  "count": 1,
  "transfers": [
    {
      "token": "a1b2c3d4e5f6a7b8",
      "title": "Offerte Q3",
      "created_at": "2026-06-17T09:12:00+00:00",
      "expires_at": "2026-06-24T09:12:00+00:00",
      "unlimited": false,
      "revoked": false,
      "files": 3,
      "size_bytes": 8412300,
      "downloads": 2,
      "recipients": 1,
      "url": "https://downloadlink.nl/p/a1b2c3d4e5f6a7b8"
    }
  ]
}

GET /api/v1/transfers/<token>

Eén transfer: metadata, de bestanden, én recente download-activiteit (wie/wanneer/welk bestand).

{
  "token": "a1b2c3d4e5f6a7b8",
  "title": "Offerte Q3",
  "revoked": false,
  "downloads_used": 2,
  "max_downloads": null,
  "size_bytes": 8412300,
  "files": [ { "name": "offerte.pdf", "size_bytes": 412300 } ],
  "downloads": 2,
  "url": "https://downloadlink.nl/p/a1b2c3d4e5f6a7b8",
  "activity": [
    { "downloaded_at": "2026-06-17T10:30:00+00:00", "type": "zip", "file": "(hele pakket / zip)", "ip": "203.0.113.7" }
  ]
}

Rate limit: 120 verzoeken per minuut per sleutel (HTTP 429 bij overschrijding).

2b. Transfer aanmaken (schrijven)

Lever een bestand af via je eigen gebrande downloadpagina, direct vanuit je systeem — bijvoorbeeld een gegenereerd rapport of factuur:

curl -X POST https://downloadlink.nl/api/v1/transfers   -H "Authorization: Bearer <sleutel>"   -F "file=@rapport.pdf"   -F "title=Rapport week 30"   -F "expiry_days=30"        # of 'never' voor onbeperkt geldig
  # optioneel: -F "password=geheim" voor een wachtwoord op de downloadpagina
HTTP 201
{
  "ok": true,
  "token": "a1b2c3d4e5f6a7b8",
  "url": "https://downloadlink.nl/p/a1b2c3d4e5f6a7b8",
  "expires_at": "2026-08-22T10:30:00+00:00",
  "unlimited": false
}

Foutpaden: 402 payment_required (schrijf-API zit in betaalde plannen), 402 quota_exceeded (opslag vol), 413 (bestand groter dan de API-limiet — gebruik daarvoor de uploadpagina). De branding van de downloadpagina volgt het account van de sleutel.

3. Webhooks

Registreer een https-URL op je accountpagina (de knop "Test" stuurt direct een ping-event om je integratie te controleren). Zodra iemand je transfer downloadt, sturen we een POST met dit event:

POST https://jouw-server.nl/webhooks/downloadlink
X-Downloadlink-Event: transfer.downloaded
X-Downloadlink-Signature: sha256=<hmac>
Content-Type: application/json

{
  "event": "transfer.downloaded",
  "delivered_at": "2026-06-17T10:30:00+00:00",
  "data": {
    "token": "a1b2c3d4e5f6a7b8",
    "title": "Offerte Q3",
    "url": "https://downloadlink.nl/p/a1b2c3d4e5f6a7b8",
    "download_type": "zip",
    "downloaded_at": "2026-06-17T10:30:00+00:00"
  }
}

Handtekening verifiëren

Bereken HMAC-SHA256 over de ruwe request-body met je webhook-secret en vergelijk constant-time met de header. Negeer berichten die niet kloppen.

Python

import hmac, hashlib

def is_valid(secret: str, raw_body: bytes, header: str) -> bool:
    expected = "sha256=" + hmac.new(secret.encode(), raw_body, hashlib.sha256).hexdigest()
    return hmac.compare_digest(expected, header or "")

Node.js

const crypto = require('crypto');

function isValid(secret, rawBody, header) {
  const expected = 'sha256=' + crypto.createHmac('sha256', secret).update(rawBody).digest('hex');
  const a = Buffer.from(expected), b = Buffer.from(header || '');
  return a.length === b.length && crypto.timingSafeEqual(a, b);
}

Antwoord met HTTP 2xx om de levering te bevestigen. Na 15 mislukte pogingen schakelen we de webhook uit; een geslaagde test (knop op je accountpagina) zet 'm weer aan. Alleen publieke https-URL's zijn toegestaan.