Første EU-frist for DPP (Batterier): 130 dage Bliv compliant nu
Sprog
EN DE FR IT ES NL PL BG CS DA EL ET FI HR HU LT LV MT PT RO SK SL SV
Produkt
Funktioner Eftersalg Sådan fungerer det Demo Enterprise Priser
Sektorer
Alle sektorer Tekstiler Elektronik Batterier
Ressourcer
Blog Sammenlign DPP-software Krav pr. land Vurdering af parathed Tjek af miljøanprisninger Gratis downloads Ordliste
Virksomhed
Partnere Kontakt
Log ind Kom gratis i gang
Udviklere / REST API

API-reference

Alt i MyProductPassport er tilgængeligt via et REST API med nøglegodkendelse: opret produkter, generér og offentliggør digitale produktpas, send aktuelle batteridata og tjek overensstemmelse direkte fra dit ERP, PIM eller build-pipeline.

v1 https://myproductpassport.eu/api/v1 Kom gratis i gang OpenAPI-specifikation ↓

01 / Kom i gangGodkendelse

Hver forespørgsel godkendes med en API-nøgle sendt som Bearer-token. Nøgler oprettes i appen under API-nøgler, vises én gang og gemmes hashet; hver nøgle har sit eget sæt tilladelser, en valgfri IP-tilladelsesliste og en valgfri udløbsdato. Nøgler kan roteres uden nedetid.

Forespørgselsheader
Authorization: Bearer pk_your_api_key
På alle abonnementer. API-nøgler kan oprettes og bruges på alle abonnementer, også det gratis. Abonnementet afgør, hvor mange forespørgsler en nøgle må sende i minuttet (nedenfor), og hvor mange produkter og pas arbejdsområdet må have.
Testtilstand. En testnøgle (pk_test_...) udfører hvert kald præcis som en live-nøgle, med samme validering, id'er og svar, og fortryder det derefter: intet gemmes, ingen e-mail eller webhook sendes, og ingen fil beholdes. Svarene indeholder "test_mode": true og headeren X-MPP-Mode: test. Byg og test en integration mod dine rigtige data, og skift derefter til en live-nøgle.

Tilladelser gives pr. nøgle, så en integration kun får det, den har brug for:

TilladelseTilladelser
products:readLæs produkter
products:writeOpret, opdater og slet produkter
passports:readLæs pas
passports:writeGenerér pas
passports:publishOffentliggør og arkivér pas
webhooks:manageOpret, test og fjern webhook-endepunkter
items:readRead individual items and their history
items:writeAdd, update and flag individual items
aftersales:readRead owner registrations and service requests
aftersales:writeUpdate service requests and reply to customers

02 / Kom i gangGrænser for forespørgsler

Grænser gælder pr. nøgle pr. minut og fastsættes af planen:

PlanForespørgsler / minut
Gratis30
Micro60
E-etiket60
Starter120
Professional300
Business600
Battery600

Hvert svar indeholder headerne X-RateLimit-Limit og X-RateLimit-Remaining. Overskrides grænsen, returneres 429:

429 Too Many Requests
{ "error": "Rate limit exceeded.", "limit": 300, "retry_after": 60 }

03 / Kom i gangFejl

Fejl er JSON med en almindelig statuskode. De mest almindelige:

StatusBetydningEksempel på indhold
401Manglende, ugyldig, tilbagekaldt eller udløbet nøgle{"error": "Invalid or revoked API key."}
403Nøglen mangler en tilladelse, IP-adressen er ikke på listen over tilladte, eller abonnementets grænse er nået{"message": "API key does not have 'products:write' permission."}
404Ressourcen findes ikke i dit arbejdsområde{"message": "Not found."}
422Validering mislykkedes{"message": "…", "errors": {"gtin": ["…"]}}
429Grænse for forespørgsler overskredet{"error": "Rate limit exceeded."}

04 / Kom i gangSideinddeling

Liste-slutpunkter returnerer 25 elementer pr. side med standardobjekterne links og meta. Angiv ?page=2 for at bladre gennem samlingen.

05 / Kom i gangForbindelse til AI-assistenter (MCP)

Forbind Claude, Cursor eller enhver assistent, der taler Model Context Protocol, og bed den med almindelige ord om at oprette produkter, udfylde pas med det, du fortæller, og tjekke, hvad der stadig mangler. Den bruger en API-nøgle med nøglens tilladelser og grænse. Den kan oprette kladder og udfylde felter; den offentliggør, arkiverer eller sletter aldrig noget: det bliver hos dig i appen.

Serveradresse (Streamable HTTP)
https://myproductpassport.eu/api/mcp
Claude Code
claude mcp add --transport http myproductpassport https://myproductpassport.eu/api/mcp \
  --header "Authorization: Bearer pk_live_your_key"
Cursor (mcp.json)
{
  "mcpServers": {
    "myproductpassport": {
      "url": "https://myproductpassport.eu/api/mcp",
      "headers": { "Authorization": "Bearer pk_live_your_key" }
    }
  }
}
Claude Desktop og andre klienter, der starter en lokal server
{
  "mcpServers": {
    "myproductpassport": {
      "command": "npx",
      "args": ["mcp-remote", "https://myproductpassport.eu/api/mcp", "--header", "Authorization: Bearer pk_live_your_key"]
    }
  }
}

De værktøjer, den tilbyder:

VærktøjHvad det gør
list_productsArbejdsområdets produkter, nyeste først, 25 pr. side, med branche og seneste pas.
get_productÉt produkt med oplysninger, branche, lovgivningsafsnit og seneste pas.
list_sectorsDe brancheskabeloner, et produkt kan bruge (tekstiler, elektronik, batterier, vin og mere), med deres id'er. Et produkts branche afgør, hvilke pasfelter der er obligatoriske.
create_productTilføjer et produkt til arbejdsområdet. Brug et sector_id fra list_sectors. compliance_sections tilføjer lovgivningsafsnit til passet: gpsr, epr, france, chemicals, eudr.
list_passportsArbejdsområdets pas, nyeste først, 25 pr. side, med status (draft, published, archived), fuldstændighed i procent og offentlig adresse.
get_passportÉt pas: status, version, fuldstændighed i procent, offentlig adresse og links til QR-koden.
create_passportOpretter en paskladde til et produkt. Den offentliggøres ikke: det gør en person i appen.
get_passport_fieldsHvad et pas beder om: nøglerne til obligatoriske og valgfrie felter, hvad hvert felt betyder (etiket, beskrivelse, eksempel), de nuværende værdier og hvilke obligatoriske felter der mangler.
update_passport_fieldsSkriver feltværdier i en kladde eller et offentliggjort pas (et offentliggjort pas opdateres på stedet: samme adresse, samme QR-kode). Nøgler fra get_passport_fields; en tom tekst fjerner en værdi. Skriv kun fakta, som brugeren eller dennes dokumenter oplyser.
get_compliancePassets fuldstændighed: procent, status og de obligatoriske felter, der stadig mangler.
Prøv med en testnøgle. Med en testnøgle (pk_test_...) bliver assistentens ændringer kontrolleret og derefter fortrudt, så du kan se, hvad den ville gøre, før du giver den en rigtig nøgle.

06 / SlutpunkterKonto

GET /me

Returnerer den godkendte konto, dens abonnementsniveau og hvor meget af produktkvoten der er brugt. Nyttigt som forbindelsestest.

Forespørgsel
curl https://myproductpassport.eu/api/v1/me \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": {
    "id": 42,
    "name": "Jane Doe",
    "email": "[email protected]",
    "company_name": "Acme Ltd",
    "subscription_tier": "professional",
    "product_count": 128,
    "product_limit": 500,
    "passport_count": 96,
    "organization": {"id": 7, "name": "Acme Ltd"},
    "api_key": {"name": "ERP sync", "permissions": ["*"], "rate_limit_per_minute": 1000, "expires_at": null},
    "webhooks_available": true
  }
}

07 / SlutpunkterProdukter

GET /products kræver products:read

Viser produkterne i dit arbejdsområde, nyeste først, 25 pr. side. Hvert produkt indeholder sin sektor og en oversigt over det seneste pas.

ParameterTypeBeskrivelse
pageintegerSidenummer.
Forespørgsel
curl "https://myproductpassport.eu/api/v1/products?page=1" \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": [
    {
      "id": 512,
      "name": "Alpine Merino Crew Sweater",
      "sku": "AM-CREW-01",
      "gtin": "05012345678900",
      "brand": "Northloom",
      "category": "textiles",
      "status": "active",
      "country_of_origin": "PT",
      "weight": 0.4,
      "weight_unit": "kg",
      "materials": [
        { "name": "Merino wool (RWS)", "percentage": 78 },
        { "name": "Recycled nylon (GRS)", "percentage": 20 },
        { "name": "Elastane", "percentage": 2 }
      ],
      "sector": { "id": 3, "name": "Textiles" },
      "latest_passport": {
        "id": 96, "version": 1,
        "status": "published", "compliance_percentage": 100
      },
      "created_at": "2026-08-14T09:21:00+00:00",
      "updated_at": "2026-09-01T16:02:11+00:00"
    }
  ],
  "links": { "next": null },
  "meta": { "current_page": 1, "per_page": 25, "total": 1 }
}
POST /products kræver products:write

Opretter ét produkt. Returnerer 403, hvis planens produktkvote er brugt op.

ParameterTypeBeskrivelse
namestringpåkrævetProduktnavn, op til 255 tegn.
skustringDit interne SKU, op til 100 tegn.
gtinstringGTIN-8, 12, 13 eller 14 (kun cifre).
brandstringBrand vist på det offentlige pas.
descriptionstringOp til 2.000 tegn.
categorystringKategori i fritekst. Standard er "general".
sector_idintegerEt sektor-id, der vælger passets feltskabelon.
country_of_originstringLandekode, f.eks. "PT".
weightnumberNettovægt.
weight_unitstringEt af kg, g, lb, oz. Standard er kg.
materialsarrayObjekter af {name, percentage 0-100}.
has_packagingbooleanTilføjer emballageskabelonens felter (nøgler, der begynder med pkg_) til passet, under den samme QR-kode.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/products \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Alpine Merino Crew Sweater",
    "sku": "AM-CREW-01",
    "gtin": "05012345678900",
    "sector_id": 3,
    "materials": [
      {"name": "Merino wool (RWS)", "percentage": 78},
      {"name": "Recycled nylon (GRS)", "percentage": 22}
    ]
  }'
Svar
{
  "data": {
    "id": 513,
    "name": "Alpine Merino Crew Sweater",
    "sku": "AM-CREW-01",
    "status": "active",
    "sector": { "id": 3, "name": "Textiles" },
    "created_at": "2026-09-07T18:40:00+00:00"
  }
}
POST /products/bulk kræver products:write

Opretter op til 100 produkter i ét kald. Hele batchen afvises med 403, hvis den ville overskride din resterende produktkvote. Til kataloger med tusindvis af produkter kan du kalde dette slutpunkt i en løkke eller bruge CSV-import i appen.

ParameterTypeBeskrivelse
productsarraypåkrævet1-100 produktobjekter med de samme felter som Opret et produkt (uden materialer).
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/products/bulk \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "products": [
      {"name": "PSL-BT-122000", "sku": "PSL-BT-122000", "sector_id": 5},
      {"name": "PSL-BT-123000", "sku": "PSL-BT-123000", "sector_id": 5}
    ]
  }'
Svar
{
  "message": "2 product(s) created.",
  "products": [
    { "id": 514, "name": "PSL-BT-122000", "status": "active" },
    { "id": 515, "name": "PSL-BT-123000", "status": "active" }
  ]
}
GET /products/{id} kræver products:read

Returnerer ét produkt med dets sektor og en oversigt over det seneste pas. 404, hvis id'et ikke er i dit arbejdsområde.

Forespørgsel
curl https://myproductpassport.eu/api/v1/products/512 \
  -H "Authorization: Bearer pk_your_key"
PUT /products/{id} kræver products:write

Opdaterer et produkt delvist. Send kun de felter, du vil ændre; feltlisten svarer til Opret et produkt.

Forespørgsel
curl -X PUT https://myproductpassport.eu/api/v1/products/512 \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"brand": "Northloom"}'
DELETE /products/{id} kræver products:write

Soft-sletter et produkt. Offentliggjorte pas for produktet fortsætter med at virke, så trykte QR-koder aldrig står uden side.

Forespørgsel
curl -X DELETE https://myproductpassport.eu/api/v1/products/512 \
  -H "Authorization: Bearer pk_your_key"
Svar
{ "message": "Product deleted." }

08 / SlutpunkterPas

GET /passports kræver passports:read

Viser pas, nyeste først, 25 pr. side, med produktoversigt og alle pasfelter.

ParameterTypeBeskrivelse
pageintegerSidenummer.
Forespørgsel
curl https://myproductpassport.eu/api/v1/passports \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": [
    {
      "id": 96,
      "uuid": "36ff3776-d517-4228-8cde-9208136ea84a",
      "version": 1,
      "status": "published",
      "compliance_status": "compliant",
      "compliance_percentage": 100,
      "public_url": "https://myproductpassport.co.uk/p/36ff3776-…",
      "gs1_url": "https://myproductpassport.co.uk/01/05012345678900",
      "product": { "id": 512, "name": "Alpine Merino Crew Sweater", "sku": "AM-CREW-01" },
      "fields": [
        { "key": "material_composition", "value": "…", "verification_status": "verified" }
      ],
      "published_at": "2026-08-16T10:00:00+00:00"
    }
  ],
  "meta": { "current_page": 1, "per_page": 25, "total": 1 }
}
POST /products/{productId}/passports kræver passports:write

Genererer et kladdepas for et produkt og udfylder felter på forhånd fra produktdata og sektorskabelonen. Returnerer kladden med dens compliance-score. Et produkt, der allerede har et live pas, returnerer 409 med det pas: ret det med PUT /passports/{id}/fields, som bevarer dets adresse og QR-kode.

Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/products/512/passports \
  -H "Authorization: Bearer pk_your_key"
GET /passports/{id} kræver passports:read

Returnerer ét pas med produkt, felter, offentlig URL og GS1 Digital Link.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96 \
  -H "Authorization: Bearer pk_your_key"
POST /passports/{id}/publish kræver passports:publish

Offentliggør et kladdepas, så dets offentlige side og QR-kode går live. Kun kladder kan offentliggøres; alt andet returnerer 404.

Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/publish \
  -H "Authorization: Bearer pk_your_key"
POST /passports/{id}/archive kræver passports:publish

Arkiverer et pas og tager dets offentlige side ud af cirkulation.

Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/archive \
  -H "Authorization: Bearer pk_your_key"
POST /passports/bulk-publish kræver passports:publish

Offentliggør op til 50 kladdepas i ét kald og rapporterer resultatet pr. pas, så én fejl aldrig afbryder batchen.

ParameterTypeBeskrivelse
passport_idsarraypåkrævet1-50 pas-id'er.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/bulk-publish \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"passport_ids": [96, 97, 98]}'
Svar
{
  "published": 2,
  "failed": 1,
  "published_ids": [96, 97],
  "errors": [
    { "id": 98, "error": "Compliance below the publishing threshold." }
  ]
}
POST /passports/{id}/successor kræver passports:write

For et produkt, der er forberedt til genbrug, omdannet eller genfremstillet, kræver batteriforordningen (artikel 77, stk. 7) et nyt pas knyttet til det oprindelige. Dette opretter en ny produktpost og et kladdepas udfyldt på forhånd fra det offentliggjorte, med link tilbage til det. Originalen forbliver live, og begge pas viser linket. Offentliggør det nye med POST /passports/{id}/publish.

ParameterTypeBeskrivelse
stagestringpåkrævetprepared_for_reuse, repurposed eller remanufactured.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/successor \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{ "stage": "repurposed" }'
Svar
{
  "data": {
    "id": 131, "status": "draft", "version": 1,
    "lineage": {
      "stage": "repurposed",
      "original": { "id": 96, "url": "https://myproductpassport.co.uk/p/..." },
      "originals": [{ "passport_id": 96, "product_id": 40, "stage": "repurposed", "status": "published", "url": "https://myproductpassport.co.uk/p/..." }],
      "successors": []
    }
  }
}
GET /passports/{id}/fields kræver passports:read

Returnerer de feltnøgler, som passets sektorskabelon beder om (påkrævede og valgfrie), de aktuelle værdier og hvilke påkrævede nøgler der stadig mangler. Brug det til at bygge indholdet til PUT /passports/{id}/fields.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/fields \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "passport_id": 96,
  "sector": "batteries",
  "compliance_percentage": 84,
  "required": ["battery_category", "carbon_footprint", "..."],
  "optional": ["energy_round_trip_efficiency", "..."],
  "missing_required": ["carbon_footprint_class", "recycled_content"],
  "values": { "battery_category": "Industrial", "...": "..." }
}
PUT /passports/{id}/fields kræver passports:write

Skriver et vilkårligt sæt feltværdier på et kladde- eller live-pas: det fulde sæt fra bilag XIII for et batteri, felterne fra en sektorskabelon eller dine egne nøgler. Send kun de nøgler, du vil ændre; en null- eller tom værdi fjerner feltet. Et live-pas opdateres på stedet, dets adresse og QR-kode ændres ikke, og dets maskinoversættelser genereres igen. Compliance scores igen. En kladde publiceres ikke af dette kald; brug POST /passports/{id}/publish.

ParameterTypeBeskrivelse
fieldsobjectpåkrævetTilknytning af feltnøgle til værdi. Nøgler er små bogstaver, cifre og understregninger; værdier op til 5.000 tegn. Op til 200 nøgler pr. kald.
Forespørgsel
curl -X PUT https://myproductpassport.eu/api/v1/passports/96/fields \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "fields": {
      "carbon_footprint": "61.2 kg CO2e/kWh",
      "carbon_footprint_class": "C",
      "recycled_content": "Cobalt 16%, lithium 6%, nickel 6%, lead 0%"
    }
  }'
Svar
{
  "message": "3 field(s) changed, 0 removed.",
  "changed": ["carbon_footprint", "carbon_footprint_class", "recycled_content"],
  "removed": [],
  "passport": { "id": 96, "status": "published", "compliance_percentage": 92 }
}
POST /passports/{id}/state-of-health kræver passports:write

Sender dette batteris egne data (bilag XIII, punkt 4, i forordning (EU) 2023/1542) til et offentliggjort pas, til BMS- og flådesystemer. Send en vilkårlig delmængde af felterne nedenfor; overensstemmelsen tjekkes igen efter opdateringen. Disse værdier vises kun for besøgende, som passets ejer har godkendt (artikel 77, stk. 2), aldrig på den offentlige side. capacity_fade, power_capability og internal_resistance gemmes som dette batteris aktuelle målinger (current_*), adskilt fra modellens oprindelige værdier.

ParameterTypeBeskrivelse
state_of_healthstringf.eks. "97% ved 412 cyklusser".
state_of_certified_energystringResterende certificeret energi (elbilbatterier).
battery_statusstringoriginal, repurposed, re-used, remanufactured eller waste.
capacity_fadestringKapacitetstab indtil nu. Gemmes som current_capacity_fade.
power_capabilitystringAktuel effektkapacitet. Gemmes som current_power_capability.
internal_resistancestringMålt intern modstand. Gemmes som current_internal_resistance.
use_datastringCyklusser, negative hændelser, temperatur og ladetilstand, op til 5.000 tegn.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/state-of-health \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "state_of_health": "97% at 412 cycles",
    "capacity_fade": "3% from initial rated capacity"
  }'
Svar
{
  "message": "2 field(s) updated.",
  "updated_fields": ["state_of_health", "current_capacity_fade"],
  "passport": { "id": 96, "status": "published", "compliance_percentage": 100 }
}
POST /passports/{id}/units kræver passports:write

Hvert batteri skal have sit eget pas (forordning (EU) 2023/1542, artikel 77, stk. 1). Registrér op til 10.000 batterier af en batterimodel i ét kald, hvert med sit eget serienummer (op til 20 bogstaver, cifre, punktummer, bindestreger eller understregninger) og eventuelt manufacturing_date, battery_status og dets data efter bilag XIII, punkt 4. Eksisterende serienumre opdateres; værdier, du udelader, bevares. Har produktet et GTIN, er hvert batteris adresse dets GS1 Digital Link, /01/{gtin}/21/{serial}. Data efter punkt 4 vises kun for besøgende, som ejeren godkender.

ParameterTypeBeskrivelse
units[].serialstringpåkrævetBatteriets serienummer.
units[].manufacturing_datestringMåned og år, f.eks. "2026-09".
units[].battery_statusstringoriginal eller waste. En statusændring kræver de værdier, der er målt ved den (bilag XIII, nr. 4, litra a); waste kræver også responsible_party_type (producer, pro eller waste_operator), responsible_party_name og responsible_party_contact (artikel 77, stk. 7). recycled, med recycled_at og recycler_name, afslutter passet (artikel 77, stk. 8). Et batteri, der er repurposed, re-used eller remanufactured, får et nyt pas: POST /passports/{id}/units/{serial}/successor.
units[].state_of_healthstringDesuden state_of_certified_energy, current_capacity_fade, current_power_capability, current_internal_resistance, remaining_capacity_ah, power_fade, internal_resistance_increase, round_trip_efficiency, round_trip_efficiency_fade, expected_lifetime_cycles_remaining, self_discharge_rate, ohmic_resistance og use_data.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/units \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"units": [{"serial": "KES-00001", "manufacturing_date": "2026-09", "state_of_health": "100%"}]}'
Svar
{ "created": 1, "updated": 0, "skipped": 0, "errors": [] }
PATCH /passports/{id}/units/{serial} kræver passports:write

For et batteristyringssystem, der sender ét batteris data: et hvilket som helst af battery_status, state_of_health, state_of_certified_energy, current_capacity_fade, current_power_capability, current_internal_resistance og use_data. Brug GET på samme sti for at læse det, eller GET /passports/{id}/units for listen (per_page op til 500).

Forespørgsel
curl -X PATCH https://myproductpassport.eu/api/v1/passports/96/units/KES-00001 \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"state_of_health": "96% at 412 cycles"}'
Svar
{
  "data": { "serial": "KES-00001", "public_url": "https://myproductpassport.co.uk/01/05012345678900/21/KES-00001", "battery_status": "original", "data": { "state_of_health": "96% at 412 cycles" } }
}
GET /passports/{id}/units/{serial}/snapshots kræver passports:read

Bilag XIII, punkt 4, litra a, kræver ydeevne- og holdbarhedsværdierne, når batteriet bringes i omsætning, og når dets status ændres. Disse målinger bevares, som de var, uanset hvad der sendes senere; send record_snapshot: true med en PATCH for også at gemme en periodisk måling.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/units/KES-00001/snapshots \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": [
    { "event": "placed_on_market", "status": "original", "values": { "state_of_health": "100%" }, "measured_at": "2026-09-26T09:00:00+00:00", "source": "api" },
    { "event": "status_change", "status": "waste", "values": { "remaining_capacity_ah": "71 Ah", "power_fade": "14%", "internal_resistance_increase": "22%", "expected_lifetime_cycles_remaining": "0" }, "measured_at": "2029-03-02T10:00:00+00:00", "source": "bms" }
  ]
}
POST /passports/{id}/units/{serial}/successor kræver passports:write

Artikel 77, stk. 7: et batteri, der er forberedt til genbrug, omdannet eller genfremstillet, har et nyt pas knyttet til sin original. Dette registrerer batteriet igen med et nyt serienummer og en ny identifikator under en second life-batterimodel i dit arbejdsområde (oprettet ud fra denne model, hvis der ikke findes en endnu), knytter de to sammen og bevarer de værdier, der blev målt ved ændringen. Det oprindelige batteri beholder sit pas. Udfyld og offentliggør second life-modellen med POST /passports/{id}/publish.

ParameterTypeBeskrivelse
stagestringpåkrævetprepared_for_reuse, repurposed eller remanufactured.
valuesobjectpåkrævetDe værdier, der er målt ved ændringen: mindst én af remaining_capacity_ah eller current_capacity_fade, af current_power_capability eller power_fade, af current_internal_resistance eller internal_resistance_increase samt expected_lifetime_cycles_remaining (bilag IV, del A).
serialstringDet nye serienummer. Standard: det oprindelige serienummer plus -RU, -RP eller -RM.
measured_atstringHvornår værdierne blev målt.
member_statestringLandekode på to bogstaver for den medlemsstat, hvor sundhedstilstanden blev testet (artikel 73, stk. 1, litra a).
target_passport_idintegerEn eksisterende second life-model af denne batterimodel, som batteriet skal registreres under.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/units/KES-00001/successor \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"stage": "repurposed", "values": {"remaining_capacity_ah": "82 Ah", "power_fade": "9%", "internal_resistance_increase": "15%", "expected_lifetime_cycles_remaining": "2000"}}'
Svar
{
  "data": {
    "serial": "KES-00001-RP", "battery_status": "repurposed", "passport_id": 131,
    "lineage": { "originals": [{ "serial": "KES-00001", "passport_id": 96, "stage": "repurposed" }], "successors": [] }
  }
}
POST /passports/{id}/registry kræver passports:write

Gemmer indsendelsen til EU's DPP-register og resultatet på et pas: status, korrelations-ID, det registreringsidentifikator, registret returnerer, og et valgfrit link til en sikkerhedskopi hostet af en DPP-tjenesteudbyder. Selve registreringen foretages i Kommissionens register (webformular eller filupload); dette holder resultatet sammen med passet. GET /passports/{id} returnerer samme blok under registry.

ParameterTypeBeskrivelse
statusstringnot_submitted, submitted, registered eller failed.
product_groupstringRegistrets produktgruppe, for eksempel batteries.
granularitystringmodel, batch eller enhed.
upistringEntydig produktidentifikator som https-URL. Standard er URL'en til det offentlige pas.
correlation_idstringKorrelations-ID tildelt af registret ved indsendelse.
uristringRegistreringsidentifikator returneret af registret.
backup_urlstringhttps-link til sikkerhedskopien, der hostes af en DPP-tjenesteudbyder.
submitted_atdateIndsendelsesdato.
registered_atdateRegistreringsdato.
errorstringFejlbeskrivelse for en mislykket indsendelse.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/registry \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "status": "registered",
    "correlation_id": "7f3a2c1e-0b4d-4f8e-9a6b-2d1c3e4f5a6b",
    "uri": "urn:eu:dpp:reg:00000001",
    "registered_at": "2027-02-18"
  }'
Svar
{
  "message": "Registry details updated.",
  "passport": {
    "id": 96,
    "registry": {
      "status": "registered",
      "upi": "https://myproductpassport.co.uk/p/552fbb4e-5d9a-41da-9050-cc9005d8b66b",
      "correlation_id": "7f3a2c1e-0b4d-4f8e-9a6b-2d1c3e4f5a6b",
      "uri": "urn:eu:dpp:reg:00000001",
      "registered_at": "2027-02-18T00:00:00+00:00"
    }
  }
}
GET /passports/{id}/qr kræver passports:read

Passets QR-kode som fil: svg (standard), png (brandet, trykklar) eller pdf (etiketark).

ParameterTypeBeskrivelse
formatstringsvg | png | pdf
Forespørgsel
curl "https://myproductpassport.eu/api/v1/passports/96/qr?format=png" \
  -H "Authorization: Bearer pk_your_key" -o passport-96.png

09 / SlutpunkterOverensstemmelse

GET /passports/{passportId}/compliance kræver passports:read

Kører et live overensstemmelsestjek af et pas mod sektorens påkrævede felter og rapporterer præcis, hvad der mangler.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/compliance \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": {
    "passport_id": 96,
    "product_name": "Alpine Merino Crew Sweater",
    "status": "compliant",
    "percentage": 100,
    "completed_fields": 12,
    "total_fields": 12,
    "missing_fields": []
  }
}

10 / SlutpunkterSektorer

GET /sectors

De sektorer, et produkt kan registreres under: platformens systemsektorer plus dem, dit arbejdsområde har defineret. Brug id'et, når du opretter produkter, og feltnøglerne, når du skriver pasfelter.

Forespørgsel
curl https://myproductpassport.eu/api/v1/sectors \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": [
    {
      "id": 4,
      "slug": "batteries",
      "name": "Batteries",
      "system": true,
      "regulations_finalised": true,
      "deadline": "2027-02-18",
      "deadline_label": "18 Feb 2027",
      "required_fields": ["battery_category", "battery_weight", "..."],
      "optional_fields": ["energy_round_trip_efficiency", "..."]
    }
  ]
}

11 / SlutpunkterDokumenter

GET /products/{productId}/documents kræver products:read

Overensstemmelseserklæringer, testrapporter og certifikater knyttet til produktet. Et offentligt dokument linkes fra hvert offentliggjort pas for produktet.

Forespørgsel
curl https://myproductpassport.eu/api/v1/products/512/documents \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": [
    {
      "id": 31,
      "product_id": 512,
      "filename": "declaration-of-conformity.pdf",
      "mime_type": "application/pdf",
      "file_size": 184322,
      "is_public": true,
      "processing_status": "completed",
      "public_url": "https://myproductpassport.co.uk/p/3f0c.../document/31",
      "created_at": "2026-09-22T10:12:00+00:00"
    }
  ]
}
POST /products/{productId}/documents kræver products:write

Multipart-upload. PDF, Word, Excel, CSV, tekst, PNG og JPEG op til 10 MB, højst 20 pr. produkt. Tekst udtrækkes i baggrunden.

ParameterTypeBeskrivelse
filefilepåkrævetDokumentet.
is_publicbooleanVis det på det offentlige pas (standard false).
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/products/512/documents \
  -H "Authorization: Bearer pk_your_key" \
  -F "[email protected]" \
  -F "is_public=1"
PATCH /products/{productId}/documents/{id} kræver products:write

Slår til eller fra, om dokumentet linkes fra det offentlige pas.

ParameterTypeBeskrivelse
is_publicbooleanpåkrævet
Forespørgsel
curl -X PATCH https://myproductpassport.eu/api/v1/products/512/documents/31 \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"is_public": false}'
DELETE /products/{productId}/documents/{id} kræver products:write

Fjerner filen og dens link til passet.

Forespørgsel
curl -X DELETE https://myproductpassport.eu/api/v1/products/512/documents/31 \
  -H "Authorization: Bearer pk_your_key"
Svar
{ "message": "Document deleted." }

12 / SlutpunkterForsyningskæde

GET /products/{productId}/supply-chain kræver products:read

Trinnene vist på produktets pas, i rækkefølge.

Forespørgsel
curl https://myproductpassport.eu/api/v1/products/512/supply-chain \
  -H "Authorization: Bearer pk_your_key"
PUT /products/{productId}/supply-chain kræver products:write

Erstatter alle trin med den liste, du sender, i den rækkefølge, den sendes. Send en tom liste for at rydde den. Trintyper: raw_material, processing, manufacturing, assembly, packaging, distribution.

ParameterTypeBeskrivelse
stepsarraypåkrævetOp til 50 trin.
steps[].step_typestringpåkrævet
steps[].supplier_namestringpåkrævet
steps[].supplier_locationstring
steps[].supplier_countrystringISO 3166-1 alpha-2.
steps[].lat / lngnumber
steps[].descriptionstring
steps[].certificationsarray
steps[].datedate
Forespørgsel
curl -X PUT https://myproductpassport.eu/api/v1/products/512/supply-chain \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"steps": [{"step_type": "raw_material", "supplier_name": "Merino Growers Co-op", "supplier_country": "NZ", "certifications": ["RWS"]}, {"step_type": "manufacturing", "supplier_name": "Northloom Mill", "supplier_location": "Biella", "supplier_country": "IT"}]}'

13 / SlutpunkterOversættelser

GET /passports/{id}/translations kræver passports:read

Hver oversat feltværdi pr. sprog med kilde: auto (maskinel, lavet ved offentliggørelse) eller manual.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/translations \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": {
    "passport_id": 96,
    "available_locales": ["bg", "cs", "da", "de", "..."],
    "translations": {
      "de": {"care_instructions": {"value": "Kalt waschen", "source": "manual"}}
    }
  }
}
PUT /passports/{id}/translations/{locale} kræver passports:write

Angiver oversættelser for ét sprog efter feltnøgle. En manuel oversættelse overskrives aldrig maskinelt. Send en tom streng for at fjerne en.

ParameterTypeBeskrivelse
fieldsobjectpåkrævetfield_key: oversat værdi
Forespørgsel
curl -X PUT https://myproductpassport.eu/api/v1/passports/96/translations/de \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"fields": {"care_instructions": "Kalt waschen, nicht bleichen"}}'
Svar
{ "message": "1 translation(s) written, 0 removed.", "locale": "de", "written": 1, "removed": 0 }

14 / SlutpunkterIntegritet og eksport

GET /passports/{id}/integrity kræver passports:read

Hver offentliggjort tilstand af passet som en hashkædet, Ed25519-signeret post: fingeraftryk (SHA-256), kædeværdi og signatur. De offentlige nøgler ligger på /.well-known/mpp-integrity-keys.json, så alle kan verificere kæden.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/integrity \
  -H "Authorization: Bearer pk_your_key"
Svar
{ "data": { "state": "intact", "hash_algorithm": "SHA-256", "signature_algorithm": "Ed25519", "records": [ { "sequence": 1, "event": "published", "content_hash": "8f3a...", "chain_hash": "c21e...", "signature": "MEUC...", "key_id": "3fa9c21e0b7d4a11" } ], "problems": [] } }
GET /passports/{id}/integrity/{sequence} kræver passports:read

Den komplette post, som den blev signeret, inklusive snapshot: hvad passet viste på det tidspunkt, helt ned til en hash af hver vedhæftet fil.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/integrity/1 \
  -H "Authorization: Bearer pk_your_key"
GET /passports/{id}/epcis kræver passports:read

Passet som et GS1 EPCIS 2.0 JSON-LD-dokument: idriftsættelsen af varen, hvert trin i forsyningskæden som en observation, individuelle batterier og et pas til andet liv som en transformation. Identifikatorer er GS1 Digital Link-URI'er, når produktet har et GTIN.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/epcis \
  -H "Authorization: Bearer pk_your_key"

15 / SlutpunkterLeverandøranmodninger

POST /passports/{id}/supplier-requests kræver passports:write

Sender en leverandør et privat link pr. e-mail, så vedkommende kan udfylde de felter, du vælger, på sit eget sprog. Intet når frem til passet, før nogen i dit arbejdsområde har godkendt det.

ParameterTypeBeskrivelse
supplier_namestringpåkrævet
supplier_emailstringpåkrævet
field_keysarraypåkrævetFeltnøgler fra passets skabelon.
localestringSprog for e-mailen og formularen, f.eks. de.
due_atdateSvarfrist; 14 dage, hvis den udelades.
messagestring
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/supplier-requests \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"supplier_name": "Mei Chen", "supplier_email": "[email protected]", "field_keys": ["recycled_content_cobalt", "carbon_footprint"], "locale": "de"}'
GET /passports/{id}/supplier-requests kræver passports:read

Alle anmodninger for passet med deres status.

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/supplier-requests \
  -H "Authorization: Bearer pk_your_key"
GET /supplier-requests/{id} kræver passports:read

Én anmodning med leverandørens svar, note og navnene på vedhæftede filer.

Forespørgsel
curl https://myproductpassport.eu/api/v1/supplier-requests/12 \
  -H "Authorization: Bearer pk_your_key"

16 / SlutpunkterEftersalg

POST /passports/{id}/items kræver items:write

Giv varer af et produkt (alle sektorer undtagen batterier, som bruger /units) deres eget serienummer: hver får sin egen adresse og QR-kode, en skjult ægthedskode til etiketten og kan registreres af sin ejer. Send op til 10.000 varer eller et interval. Med et GTIN er adressen GS1 Digital Link /01/{gtin}/21/{serial}.

ParameterTypeBeskrivelse
items[].serialstringpåkrævetOp til 20 bogstaver, tal, punktummer, bindestreger eller understregninger.
items[].batchstringBatch eller parti, op til 20 tegn.
items[].manufactured_onstringProduktionsdato, ÅÅÅÅ-MM-DD.
rangeobjectI stedet for items: prefix, start, count, digits og batch, for eksempel SN-00001 til SN-00500.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/passports/96/items \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"range": {"prefix": "SN-", "start": 1, "count": 500, "digits": 5, "batch": "B2026-10"}}'
Svar
{ "created": 500, "updated": 0, "skipped": 0, "over_limit": 0, "errors": [] }
GET /passports/{id}/items/{serial} kræver items:read

En vare med adresse, status, om den er registreret og til hvornår garantien gælder, dens ægthedstjek og historik. En nøgle med items:write får også den skjulte kode til udskrivning. GET /passports/{id}/items viser dem (filtre status og batch, per_page op til 500).

Forespørgsel
curl https://myproductpassport.eu/api/v1/passports/96/items/SN-00001 \
  -H "Authorization: Bearer pk_your_key"
Svar
{
  "data": { "serial": "SN-00001", "status": "active", "url": "https://myproductpassport.co.uk/01/05012345678900/21/SN-00001", "registered": true, "warranty_ends_on": "2028-10-02", "events": [ { "type": "registered", "country": "IE", "at": "2026-10-03T09:12:00+00:00" } ] }
}
PATCH /passports/{id}/items/{serial} kræver items:write

Sæt status til stolen eller recalled, så advarer dens side alle, der scanner den, med din status_note; en stjålet vare kan ikke registreres. retired tager siden offline. Batch og manufactured_on kan også ændres.

ParameterTypeBeskrivelse
statusstringactive, stolen, recalled eller retired.
status_notestringVises på varens side, op til 500 tegn.
Forespørgsel
curl -X PATCH https://myproductpassport.eu/api/v1/passports/96/items/SN-00001 \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"status": "stolen", "status_note": "Reported stolen on 2 October 2026."}'
GET /owner-registrations kræver aftersales:read

Personer, der har registreret dine produkter: navn, e-mail, land, købsdato, forhandler, garantidatoer, og om de har sagt ja til nyheder og tilbud (marketing_consent=1 viser kun dem). Aktive registreringer som standard; status=pending, transferred eller ended for andre; since= for ændringer efter en dato.

Forespørgsel
curl "https://myproductpassport.eu/api/v1/owner-registrations?marketing_consent=1&since=2026-10-01" \
  -H "Authorization: Bearer pk_your_key"
GET /service-requests kræver aftersales:read

Reparationer, garantikrav, tilbagetagninger, reservedele og spørgsmål sendt fra dine pas, nyeste først, med filtre status og type. GET /service-requests/{reference} tilføjer samtalen.

Forespørgsel
curl "https://myproductpassport.eu/api/v1/service-requests?status=new" \
  -H "Authorization: Bearer pk_your_key"
POST /service-requests/{reference}/replies kræver aftersales:write

Dit svar mailes til kunden med et link til henvendelsens side, på kundens sprog. internal: true tilføjer en note, som kun dit team ser. PATCH /service-requests/{reference} med en status fører den videre (kunden får besked, når den er i gang, løst eller lukket).

ParameterTypeBeskrivelse
bodystringpåkrævetSvaret, op til 5.000 tegn.
internalbooleanEn note til dit team i stedet for et svar.
statusstringnew, in_progress, waiting, resolved eller closed.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/service-requests/SR-7K3F9Q/replies \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"body": "A new lid is on its way today.", "status": "waiting"}'

17 / SlutpunkterMasseredigering og billeder

PATCH /products/bulk-fields kræver products:write

Angiver en produktoplysning eller et pasfelt på op til 5.000 produkter. mode er set, fill (kun hvor feltet er tomt) eller clear. Op til 100 produkter opdateres i selve forespørgslen; større mængder sættes i kø (202).

ParameterTypeBeskrivelse
product_idsarraypåkrævet
targetstringpåkrævetproduct | field
keystringpåkrævet
valuestring
modestringset | fill | clear
Forespørgsel
curl -X PATCH https://myproductpassport.eu/api/v1/products/bulk-fields \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"product_ids": [12, 13, 14], "target": "field", "key": "warranty_period", "value": "10 years", "mode": "fill"}'
Svar
{ "data": { "changed": 2, "skipped": 1, "errors": [] } }
POST /products/{id}/images kræver products:write

Multipart-upload af en JPG, PNG eller WebP (op til 15MB, 8 pr. produkt). Det første billede er forsidebilledet på det offentlige pas.

ParameterTypeBeskrivelse
imagefilepåkrævet
altstringBeskrivelse af billedet.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/products/12/images \
  -H "Authorization: Bearer pk_your_key" \
  -F [email protected] -F alt="Front of the battery"
PUT /products/{id}/images/order kræver products:write

Angiv image_ids i den ønskede rækkefølge; det første bliver forsidebillede.

ParameterTypeBeskrivelse
image_idsarraypåkrævet
Forespørgsel
curl -X PUT https://myproductpassport.eu/api/v1/products/12/images/order \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"image_ids": [31, 30]}'
DELETE /products/{id}/images/{imageId} kræver products:write

Fjerner billedet og dets fil.

Forespørgsel
curl -X DELETE https://myproductpassport.eu/api/v1/products/12/images/31 \
  -H "Authorization: Bearer pk_your_key"

18 / SlutpunkterWebhooks

GET /webhooks kræver webhooks:manage

De endpoints, der er registreret for dit arbejdsområde. Hemmeligheder er ikke med her; hent ét endpoint for at se dets hemmelighed.

Forespørgsel
curl https://myproductpassport.eu/api/v1/webhooks \
  -H "Authorization: Bearer pk_your_key"
POST /webhooks kræver webhooks:manage

Registrerer en offentlig HTTPS-URL til en eller flere hændelser. Svaret indeholder signeringshemmeligheden. Private eller interne værter afvises.

ParameterTypeBeskrivelse
urlstringpåkrævet
eventsarraypåkrævetEn af hændelserne nedenfor.
Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/webhooks \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"url": "https://erp.acme.example/mpp", "events": ["passport.published", "product.updated"]}'
Svar
{
  "data": {
    "id": 3,
    "url": "https://erp.acme.example/mpp",
    "events": ["passport.published", "product.updated"],
    "is_active": true,
    "failure_count": 0,
    "secret": "9f1c...64 hex characters...",
    "created_at": "2026-09-22T10:12:00+00:00"
  }
}
GET /webhooks/{id} kræver webhooks:manage

Forespørgsel
curl https://myproductpassport.eu/api/v1/webhooks/3 \
  -H "Authorization: Bearer pk_your_key"
PUT /webhooks/{id} kræver webhooks:manage

Skift URL eller hændelser, eller sæt slutpunktet på pause og genoptag det. Genoptagelse nulstiller antallet af fejl; et slutpunkt sættes automatisk på pause efter 10 fejlslagne leveringer i træk.

ParameterTypeBeskrivelse
urlstring
eventsarray
is_activeboolean
Forespørgsel
curl -X PUT https://myproductpassport.eu/api/v1/webhooks/3 \
  -H "Authorization: Bearer pk_your_key" \
  -H "Content-Type: application/json" \
  -d '{"is_active": true}'
POST /webhooks/{id}/test kræver webhooks:manage

Sætter en webhook.test-levering i kø, så du kan tjekke din modtager og signaturkode.

Forespørgsel
curl -X POST https://myproductpassport.eu/api/v1/webhooks/3/test \
  -H "Authorization: Bearer pk_your_key"
Svar
{ "message": "Test delivery queued." }
GET /webhooks/{id}/deliveries kræver webhooks:manage

Seneste leveringer, nyeste først, med den HTTP-status, dit slutpunkt returnerede, og de første 500 tegn af svaret.

ParameterTypeBeskrivelse
per_pageintegerOp til 100.
Forespørgsel
curl https://myproductpassport.eu/api/v1/webhooks/3/deliveries \
  -H "Authorization: Bearer pk_your_key"
DELETE /webhooks/{id} kræver webhooks:manage

Forespørgsel
curl -X DELETE https://myproductpassport.eu/api/v1/webhooks/3 \
  -H "Authorization: Bearer pk_your_key"
Svar
{ "message": "Webhook endpoint deleted." }

19 / HændelserWebhooks

I stedet for at polle kan du registrere et webhook-slutpunkt i appen (siden Webhooks, tilgængelig fra Starter-planen og op), så sender MyProductPassport JSON via POST til din URL, når der sker noget:

HændelseUdløses når
product.createdEt produkt oprettes (app, API eller CSV-import)
product.updatedEt produkt opdateres
product.deletedEt produkt slettes
passport.createdEt pas genereres
passport.publishedEt pas bliver aktivt
passport.archivedEt pas arkiveres
supplier_request.submittedEn leverandør sender de oplysninger, du har bedt om
owner.registeredEn ejer bekræfter sin registrering
owner.transferredEn vare overgår til en ny registreret ejer
service_request.createdEn kunde sender en servicehenvendelse fra et pas
service_request.updatedEn servicehenvendelse får et svar eller en ny status
item.status_changedEn vare markeres som stjålet, tilbagekaldt eller udfaset eller frigives igen
item.verification_failedEn scanning af et sikkert tag mislykkes, forkerte koder hober sig op, eller et serienummer ses for mange steder
webhook.testDu sender en testlevering fra appen

Hver levering er en JSON-konvolut: et leverings-id (samme id sendes igen ved gentagelser, så du kan fjerne dubletter), hændelsen, forsøgsnummeret, et tidsstempel og hændelsesdata. Pashændelser indeholder passets uuid og offentlige URL, så du sjældent har brug for en ekstra forespørgsel:

Leveringens indhold
{
  "id": 8123,
  "event": "passport.published",
  "attempt": 1,
  "created_at": "2026-09-22T10:12:00+00:00",
  "data": {
    "passport_id": 96,
    "uuid": "3f0c8f1e-...",
    "version": 2,
    "status": "published",
    "public_url": "https://myproductpassport.co.uk/p/3f0c8f1e-...",
    "product_id": 512,
    "product": {"id": 512, "name": "Alpine Merino Crew Sweater", "sku": "NL-AMC-001", "gtin": "5012345678900"}
  }
}

Headerne indeholder hændelsesnavnet, leverings-id'et, et Unix-tidsstempel og en HMAC-signatur af den rå body, så du kan verificere, at den kom fra os, og afvise gentagelser:

Leveringens headere
Content-Type: application/json
User-Agent: MyProductPassport-Webhooks/1.0
X-MPP-Event: passport.published
X-MPP-Delivery: 8123
X-MPP-Timestamp: 1790084320
X-MPP-Signature: sha256=<hex hmac of the raw body, keyed with your endpoint secret>

Svar med en vilkårlig 2xx inden for 10 sekunder. Alt andet forsøges igen fem gange over ca. 90 minutter (30 s, 1 min, 5 min, 15 min, 1 t); efter 10 fejl i træk sættes endpointet på pause, indtil du genaktiverer det.

Verificér (PHP)
$expected = 'sha256=' . hash_hmac('sha256', $rawBody, $endpointSecret);
abort_unless(hash_equals($expected, $request->header('X-MPP-Signature')), 401);