Ga naar inhoud

Quickstart

Deze quickstart draait volledig in de sandbox op https://api.eftisandbox.app. Er wordt niets vervoerd en niets gefactureerd; sandbox-data staat los van live-data.

  1. Elke call gaat met Authorization: Bearer <key>. De prefix bepaalt de modus: sk_test_ praat met de sandbox, sk_live_ met productie.

    Zet de key in je omgeving zodat hij niet in je shell-geschiedenis of je repo belandt:

    Terminal window
    export FREIGHTAPI_KEY="sk_test_..."
    export FREIGHTAPI_BASE_URL="https://api.eftisandbox.app"

    Controleer of de key werkt:

    Terminal window
    curl -s "$FREIGHTAPI_BASE_URL/v1/shipments?limit=1" \
    -H "Authorization: Bearer $FREIGHTAPI_KEY"

    Een 401 met code invalid_api_key betekent dat de key niet bestaat of is ingetrokken; zie Foutcodes.

  2. Een zending heeft minimaal een afzender, een vervoerder, een geadresseerde, een laadadres, een losadres en goederen. Alles daarbuiten is optioneel en vult de eFTI-dataset verder aan.

    Terminal window
    curl -s -X POST "$FREIGHTAPI_BASE_URL/v1/shipments" \
    -H "Authorization: Bearer $FREIGHTAPI_KEY" \
    -H "Content-Type: application/json" \
    -d '{
    "reference": "ORD-1042",
    "transport_type": "international",
    "consignor": {
    "name": "Demo Logistics B.V.",
    "address": { "street": "Havenweg 12", "postal_code": "3089 JG", "city": "Rotterdam", "country": "NL" }
    },
    "carrier": {
    "name": "Transport Nowak Sp. z o.o.",
    "address": { "street": "ul. Przemyslowa 8", "postal_code": "61-001", "city": "Poznan", "country": "PL" }
    },
    "consignee": {
    "name": "Mueller Maschinenbau GmbH",
    "address": { "street": "Industriestrasse 4", "postal_code": "70565", "city": "Stuttgart", "country": "DE" }
    },
    "pickup": { "address": { "street": "Havenweg 12", "postal_code": "3089 JG", "city": "Rotterdam", "country": "NL" } },
    "delivery": { "address": { "street": "Industriestrasse 4", "postal_code": "70565", "city": "Stuttgart", "country": "DE" } },
    "goods": [
    { "description": "CNC machine parts", "quantity": 12, "package_type": "pallet", "gross_weight_kg": 8400 }
    ]
    }'

    Je krijgt 201 Created terug met de volledige zending:

    {
    "id": "shp_01M2FP3DE7YQ1Z24SBT4317SM2",
    "mode": "test",
    "status": "draft",
    "version": 1,
    "current_version": {
    "id": "ver_01M2FP3DE7HZH0ENF0VH2CKXVB",
    "version": 1,
    "document_hash": "54db818c1f898ad691916212ecba15582f56a9c4e3edef4850c5e62abc24da57"
    },
    "warnings": [
    {
    "path": "consignee.contact",
    "code": "consignee_contact_for_delivery_signature",
    "message": "Without an email address or phone number for the consignee no signature can be requested on delivery."
    }
    ]
    }

    Bewaar de id:

    Terminal window
    export SHIPMENT_ID="shp_01M2FP3DE7YQ1Z24SBT4317SM2"
  3. Zolang een zending draft is, verandert ze vrij. Uitgeven bevriest de vrachtbriefvelden en zet de eerste schakel in de hash-keten.

    Terminal window
    curl -s -X POST "$FREIGHTAPI_BASE_URL/v1/shipments/$SHIPMENT_ID/issue" \
    -H "Authorization: Bearer $FREIGHTAPI_KEY" \
    -H "Content-Type: application/json" \
    -d '{}'

    De status staat nu op issued en issued_at is gevuld. Een PATCH op een bevroren veld geeft vanaf nu field_frozen.

  4. Een uitgegeven zending heeft een inspectielink: een token-URL met QR-code die een chauffeur, ontvanger of handhaver zonder account kan openen.

    Terminal window
    curl -s "$FREIGHTAPI_BASE_URL/v1/shipments/$SHIPMENT_ID/inspection-link" \
    -H "Authorization: Bearer $FREIGHTAPI_KEY"
    {
    "token_id": "ins_01M2FP54YDY3DTNK4GQE1JPT8K",
    "url": "https://sign.eftisandbox.app/i/CvtAOsHboY80GbORQNUOztOW3INHRSHGFd8kQ4FN4Dc",
    "expires_at": "2027-09-14T10:07:12.845Z",
    "qr_svg": "<svg xmlns=\"http://www.w3.org/2000/svg\" ...>"
    }

    Open url in je browser, of print qr_svg op de vrachtbrief. De PNG- en SVG-varianten van de QR-code staan los op /v1/inspection-links/{token_id}/qr.png en .../qr.svg. Lekt een link, dan trek je hem in met POST /v1/shipments/{id}/inspection-link/rotate; de oude token geeft daarna token_rotated.

  5. In plaats van te pollen abonneer je een endpoint op gebeurtenissen.

    Terminal window
    curl -s -X POST "$FREIGHTAPI_BASE_URL/v1/webhook-endpoints" \
    -H "Authorization: Bearer $FREIGHTAPI_KEY" \
    -H "Content-Type: application/json" \
    -d '{
    "url": "https://example.com/hooks/freightapi",
    "events": ["shipment.issued", "shipment.delivered"],
    "description": "Quickstart"
    }'
    {
    "id": "whe_01M2FP5AJCSSDQYQVAV865N8Q0",
    "url": "https://example.com/hooks/freightapi",
    "events": ["shipment.issued", "shipment.delivered"],
    "active": true,
    "mode": "test",
    "secret": "whsec_0HBh8opWaFo6YUdG96sf8gPpk2ydhA4oxjVHuLGASSN"
    }

    Stuur jezelf een testping en verifieer de handtekening:

    Terminal window
    curl -s -X POST "$FREIGHTAPI_BASE_URL/v1/webhook-endpoints/$ENDPOINT_ID/test" \
    -H "Authorization: Bearer $FREIGHTAPI_KEY"

    In je handler verifieer je de freightapi-signature-header vóórdat je de body vertrouwt:

    import { parseEvent } from '@freightapi/sdk/webhooks'
    const event = await parseEvent({
    secret: process.env.FREIGHTAPI_WEBHOOK_SECRET!,
    header: request.headers,
    // De body exact zoals hij binnenkwam; nooit de geparste JSON opnieuw serialiseren.
    body: await request.text(),
    })
    console.log(event.type, event.data)

    Wat er bij een mislukte aflevering gebeurt — retries, de dead-letter queue en het opnieuw afspelen van een levering — staat onder Webhooks.

  6. In de sandbox hoef je niet zelf een chauffeur te spelen. simulate met action: "auto" loopt de hele levenscyclus af: ondertekenen door afzender en vervoerder, onderweg, afleveren met de handtekening van de geadresseerde.

    Terminal window
    curl -s -X POST "$FREIGHTAPI_BASE_URL/v1/test/shipments/$SHIPMENT_ID/simulate" \
    -H "Authorization: Bearer $FREIGHTAPI_KEY" \
    -H "Content-Type: application/json" \
    -d '{"action": "auto"}'

    Volg daarna wat er gebeurd is:

    Terminal window
    curl -s "$FREIGHTAPI_BASE_URL/v1/shipments/$SHIPMENT_ID/events" \
    -H "Authorization: Bearer $FREIGHTAPI_KEY"

    Elke gebeurtenis draagt een seq, een hash en de prev_hash van zijn voorganger. Of die keten klopt, controleer je met GET /v1/shipments/{id}/integrity.

  • API-reference — alle routes, direct uit te proberen tegen de sandbox.
  • Foutcodes — elke stabiele code die de API teruggeeft.
  • SDK’s — de TypeScript-client en wat er nog aankomt.