Skip to content

Muutosloki

Muutosloki

Viimeisimpien julkaisujen kuratoidut kohokohdat. Katso täydelliset API-versiot ja rikkovien muutosten käytännöt (breaking changes) sivulta API-versiointi & LTS-käytäntö.

Yksityiskohtaiset muutokset yksittäisiin päätepisteisiin: OpenAPI-määritys ja interaktiivinen API-viite.


2026-08 · Keyset-kursori nyt kaikissa lista-päätepisteissä

  • Korjaus: Kursorikorjaus päätepisteille GET /v1/codes ja GET /v1/dpp (katso alta) on nyt otettu käyttöön kaikissa muissa kursorisivutetuissa listoissa: GET /v1/qr-codes/:id/comments, /v1/workspaces, /v1/gs1/identifiers, /v1/members, /v1/audit-logs, /v1/admin/orgs, /v1/admin/users ja /v1/webhooks/:id/deliveries. Kaikki sivuttivat aiemmin pelkästään kentän created_at perusteella; rivit, joilla oli identtinen aikaleima (eräajon audit-merkinnät, webhook-uudelleenyritykset, jäsenten tuonnit), saattoivat kadota seuraavalta sivulta. Lajitteluavain on nyt kaikkialla yhdistelmä (created_at, id).
  • API-muutos: Näissä listoissa meta.pagination.next_cursor on tästä lähtien myös läpinäkymätön arvo (base64url) pelkän aikaleiman sijaan; lukukelvottomat kursorit palauttavat virheen 400, ja vanhoja aikaleimakursoreita hyväksytään edelleen siirtymäajan. Poikkeuksena GET /v1/webhooks/:id/deliveries: siellä next_cursor säilyy viimeisimmän toimituksen tunnuksena (tuntematon ID → ensimmäinen sivu). Asiakasohjelmien, jotka palauttavat arvon next_cursor muuttumattomana — Dashboard, CLI, SDK:t, MCP —, ei tarvitse muuttaa mitään.
  • Vaikutus: Ei vaadi migraatiota. Jos olet kaivannut merkintöjä jossakin näistä listoista (esim. audit-loki tai toimitusloki Dashboardissa) sivuja selatessasi: ne eivät olleet kadonneet — listat näyttävät ne tästä lähtien kokonaisuudessaan.

2026-08 · Aikaleimat muokkauksen ja poiston jälkeen jälleen OpenAPI-yhteensopivia

  • Korjaus: PATCH /v1/codes/{id} -pyynnön jälkeen updated_at palautui SQLite-muodossa ilman aikavyöhykettä (2026-08-17 09:00:00), vaikka OpenAPI-määrittely lupaa muodon format: date-time ja luominen (POST) palauttaa ISO-aikaleiman (2026-08-17T09:00:00.000Z). Sama päti kenttiin deleted_at/updated_at soft-delete-toiminnossa sekä API-avainten, organisaatioiden, työtilojen, jäsenten, kommenttien ja webhookien muokkaus- ja poistopolkuihin, ja lisäksi API-avainten last_used_at-kenttään ja webhookien last_triggered_at-kenttään. Kaikki kirjoituspolut käyttävät nyt ISO 8601 -aikaleimaa (UTC, T ja Z).
  • Vaikutus: Asiakasohjelmat, jotka jäsentävät updated_at-kentän käyttäen new Date(...) -metodia (SDK:t, CLI, Dashboard), tulkitsivat välilyönnillisen muodon paikalliseksi ajaksi — CLI näytti kerran muokattujen koodien kohdalla ajan siirtyneenä paikallisen poikkeaman (offset) verran (Wien: −2 h). Tämä on korjattu. Lisäksi tietojen migraatio normalisoi jo tallennetut vanhanmuotoiset arvot ISO-muotoon, jotta lajittelu ja vertailut toimivat oikein sekalaisten tietojen joukossa. Ei muutoksia kenttien nimiin tai vastauksen rakenteeseen.
  • Tausta: Sama virheluokka kuin kahdessa alla olevassa korjauksessa (API-avaimen vanheneminen, uudelleenskannauksen aikaraja): SQLiten datetime('now') kirjoittaa muodossa YYYY-MM-DD HH:MM:SS, kun taas kaikki muut kirjoittajat käyttävät ISO 8601 -muotoa. Lähdekoodin suojatesti estää vastaavat tapaukset jatkossa.

2026-08 · Listasivutus ei enää kadota batch-koodeja

  • Korjaus: GET /v1/codes ja GET /v1/dpp sivuttivat tietoja ainoastaan kentän created_at perusteella. Kuitenkin koodit, jotka on luotu reiteistä POST /v1/codes/batch, POST /v1/dpp/batch tai CSV/XLSX-tuonnista, jakavat yhden aikaleiman — heti kun erä (batch) oli suurempi kuin limit (oletusarvo 20), toinen sivu ei enää palauttanut saman aikaleiman jäljellä olevia rivejä. Koodit olivat olemassa ja ne olivat saatavilla reitistä GET /v1/codes/:id, mutta ne eivät koskaan näkyneet listassa (Dashboard, CLI qr3 list, SDK:t, MCP). Kursori on nyt keyset-pohjainen yhdistelmällä (created_at, id).
  • API-muutos: meta.pagination.next_cursor on tästä lähtien läpinäkymätön arvo (base64url) pelkän aikaleiman sijaan. Niiden, jotka palauttavat kursorin muuttumattomana parametrina ?cursor= — kuten Dashboard, CLI, kaikki SDK:t ja MCP-palvelin tekevät — ei tarvitse muuttaa mitään. Vanhoja aikaleimakursoreita hyväksytään edelleen siirtymäajan; lukukelvottomat kursorit palauttavat nyt tilakoodin 400 sen sijaan, että ne palauttaisivat hiljaisesti ensimmäisen sivun.
  • Vaikutus: Jos näit batch-tuonnin jälkeen listassa vähemmän koodeja kuin luotiin: koodit eivät olleet kadonneet — lista näyttää ne tästä lähtien kokonaisuudessaan. Mitään migraatiota ei tarvita.

2026-08 · Turvallisuuden uudelleenskannaukset suoritetaan jälleen 24 tunnin välein

  • Korjaus: Kohde-URL-osoitteiden ja laskeutumissivujen linkkien (Google Web Risk) jaksottainen uudelleenskannaus ohitti koodit, joiden viimeisin skannaus oli samana kalenteripäivänä kuin 24 tunnin aikaraja — kellonajasta riippuen uudelleenskannaus viivästyi jopa yhdellä lisäpäivällä. Aikaraja lasketaan nyt samassa ISO-muodossa, jossa skannauksen aikaleimat on tallennettu.
  • Vaikutus: Kohde-URL, joka luokitellaan turvattomaksi viimeisimmän skannauksen jälkeen, johtaa jälleen koodin automaattiseen keskeyttämiseen dokumentoidun 24 tunnin aikaikkunan sisällä. Ei muutoksia API- tai vastausmuotoon.

2026-08 · API-avaimet vanhenevat tarkkana vanhentumisajankohtana

  • Korjaus: API-avain, jonka expires_at oli samana päivänä, hyväksyttiin aiemmin keskiyöhön UTC asti. Vanhentumista verrataan nyt aikaleimana merkkijonon sijaan — vanhentunut avain palauttaa välittömästi virheen 401.
  • Tausta: expires_at tallennetaan ISO-aikaleimana (2026-08-14T09:00:00Z), kun taas vertailupuoli antoi välilyönnillisen muodon (2026-08-14 09:00:00). Raaka merkkijonovertailu täsmäsi siksi vain silloin, kun jo päivämäärä oli eri.
  • Vaikutus: Migraatiota ei tarvita, vastausmuoto kohteessa GET /v1/api-keys pysyy muuttumattomana. Lukukelvottomat vanhentumisarvot tulkitaan nyt vanhentuneiksi voimassa olevien sijaan.

2026-08 · API-viite: Tenant-hallinta dokumentoitu

  • OpenAPI: Spesifikaatio — ja sen myötä interaktiivinen viite — dokumentoi nyt organisaatiot (sis. GET /v1/organizations/usage), työtilat, jäsenet ja roolit sekä audit-lokit.
  • Billing: Hinnoittelun yleiskatsaus (GET /v1/billing/plans) on julkinen; Checkout (POST /v1/billing/checkout) ja Stripe-asiakasportaali (GET /v1/billing/portal) on määritelty päätepisteiksi organisaation ylläpitäjille.
  • Skannausvienti: Skannaustilastot (GET /v1/codes/{id}/scans) ja raakadatavienti (…/scans.csv, …/scans.xlsx) on dokumentoitu kokonaan — mukaan lukien GDPR-huomautus: ip_hash ei koskaan sisälly vientiin.
  • Virhekäyttäytyminen: Uutena on dokumentoitu myös pyynnön validoinnin 400-vastaus: Vastauksen runko on raaka Zod-virhe, ei RFC-7807-ongelmadokumentti — se toimitetaan kuitenkin sisältötyypillä application/problem+json.

2026-08 · Julkisten tiedostolinkkien kopiointi

  • Dashboard: Koodin tietosivulla on nyt jokaisen julkisen tiedoston kohdalla painike, joka kopioi tiedoston julkisen linkin leikepöydälle – suoraan käytettäväksi QR-koodin kohde-URL-osoitteena, kun skannauksen pitää avata heti tietty dokumentti laskeutumissivun ja sen tiedostoluettelon sijaan.
  • API: Tiedostopäätepisteet (/v1/files) palauttavat lisäksi kentän public_url. Kenttä on asetettu vain tiedostoille, joilla on visibility: public – yksityiset tiedostot eivät saa julkista osoitetta.
  • Toiminta: Linkki ei vaadi kirjautumista ja avaa tiedoston suoraan selaimessa. Tiedoston Korvaa-toiminto jättää linkin ennalleen, joten siihen osoittava tulostettu koodi pysyy voimassa. Lisätiedot: Tiedostot & datalehdet.

2026-07 · Tiimiroolit: Avustaja ilman poisto-oikeutta & ylläpitäjän laskutus

  • Uutta: Jäsenrooli Avustaja (ei poisto-oikeutta) — luo ja muokkaa QR-koodeja, tiedostoja ja Digital Product Passports -passeja, mutta ei voi poistaa mitään eikä luoda API-avaimia. Kaikki tuhoavat päätepisteet tarkistavat roolin palvelimen puolella (403).
  • Laskutus: Tilauspakettien päivitykset ja Stripe-asiakasportaali (POST /v1/billing/checkout, GET /v1/billing/portal) on nyt rajattu vain organisaation Ylläpitäjille — kaikki muut roolit näkevät tilaussivun vain luku -tilassa.
  • Dashboard: Toiminnot, joita käyttäjän oma rooli ei salli, piilotetaan käyttöliittymästä: Katselija ei esimerkiksi näe painikkeita luomiseen, muokkaamiseen tai poistamiseen, mutta listaukset, lataukset ja tilastot pysyvät näkyvissä. Lisätiedot: Tiimi & roolit.

2026-06 · Ulkoiset linkit koodin laskeutumissivulla

  • Laskeutumissivu: Koodin qr3-isännöimä laskeutumissivu voi nyt luetella ulkoisia, itse isännöityjä linkkejä ({ label, url }) ladattujen tiedostojen lisäksi tai niiden sijaan – esimerkiksi omalla sivustollasi oleville teknisille tiedoille.
  • API: POST/PATCH /v1/codes hyväksyvät links-taulukon (0–20 merkintää, http(s), ≤ 2048 merkkiä). Jokainen URL-osoite tarkistetaan Google Web Risk -palvelulla; turvaton URL-osoite palauttaa 422. Tyhjä taulukko poistaa kaikki linkit.
  • Dashboard: Lisää, järjestä uudelleen ja poista linkkejä koodin tietosivulla.
  • Tietoturva: Renderöidyt linkit pysyvät XSS-turvallisina (escapetettu, vain http(s)), ja sivu säilyttää noindex-otsakkeensa.

2026-04 · QR-koodikohtainen Dashboard-analytiikka

  • Dashboard: QR-koodiluettelon Analytics-painike avaa nyt kyseisen QR-koodin tilastosivun osoitteessa /dashboard/codes/{id}.
  • Reititys: Alias /dashboard/codes ohjaa edelleen osoitteeseen /dashboard, mutta ei enää kaappaa yksityiskohtaisia reittejä, kuten /dashboard/codes/{id}.
  • API: Yksityiskohtasivu lataa QR-koodin suoraan kutsulla GET /v1/codes/:id; tämän ansiosta se ei ole enää riippuvainen luettelon sivutusrajoista (pagination limits).
  • Testit: Regressiotestit kattavat alias-uudelleenohjauksen ja suoran koodin latauksen.

2026-04 · QR-koodien poistovalintaikkuna Dashboardissa

  • Dashboard: QR-koodiluettelon roskakorikuvake avaa nyt oman React-valintaikkunan selaimen natiivin ponnahdusikkunan sijaan.
  • Palaute: Poistamisen jälkeen näytetään toast-ilmoitus onnistumisesta tai virheestä.
  • Testit: packages/dashboard/tests/dashboard.test.ts estää regressiot confirm()-kutsussa QR-koodin poistovuossa.

2026-04 · Dynaamisten QR-koodien lyhytlinkkitesti Dashboardissa

  • Dashboard: QR-koodiluettelon lyhytkoodit (shortcodes) ovat nyt suoraan klikattavissa ulkoisina uudelleenohjauslinkkeinä. Ulkoisen linkin kuvake esimerkiksi koodin wu3qaa vieressä avaa osoitteen https://qr3.app/{shortCode} uudessa välilehdessä.
  • i18n: Työkaluvihjetekstit (tooltips) lisätty saksaksi ja englanniksi.
  • Testit: packages/dashboard/tests/dashboard.test.ts suojaa linkin href-osoitetta, uuden välilehden toimintaa, määritteitä noopener noreferrer ja kuvaketta regressioilta.

2026-04 · Ohjaus-Workerin reitti dynaamisille QR-koodeille

  • Korjaus: Redirect-Worker käsittelee jälleen dynaamiset QR-koodit osoitteessa https://qr3.app/{shortCode}. Tuotantoreitti käyttää nyt muotoa qr3.app/*, koska Cloudflare Worker -reitit eivät tue :code-polkuparametreja.
  • Vankistus: Täsmäämättömät polut välitetään eteenpäin laskeutumissivun alkuperään (landing origin), jotta Redirect-Worker ei estä normaaleja sivuja, kuten /de/pricing.
  • Testit: packages/redirect/tests/unit/redirect.test.ts testaa wildcard-reitin, lyhytkoodien käsittelyn ja alkuperän läpiviennin (origin pass-through).

2026-04 · Työtilan DPP-skannausyleiskatsaus (Q3.4.2)

  • Uutta: GET /v1/workspace/stats/dpp?days=30 — aggregoi kaikki API-avaimen työtilan dpp_scans-tapahtumat (active_dpps, scans_by_day, top_dpps tuotenimellä/kategorialla).
  • Dashboard: Aloitussivun (/dashboard) kortti, jossa on 30 päivän pylväskaavio + Top-listat — rinnakkain QR-koodikorttien kanssa.
  • Julkinen: Markkinoinnin lyhytlinkki GET /dpp/dpp_<id> (yksi segmentti) live-demoja varten, rinnakkain polun /dpp/{gtin}/{serial} kanssa.

2026-04 · DPP-skannausanalytiikka (Q3.4.1)

  • Uutta: GET /v1/dpp/:id/stats?days=30 — julkisen GS1-selvityspalvelun (resolver) aggregoidut skannaukset DPP-kohtaisesti. Kentät: total_scans, period_scans, scans_by_day, top_countries, top_devices, top_representations.
  • Uutta: Taulukko dpp_scans (migraatio 0011) — erillään taulukosta scans (Redirect-Worker). IP-osoitteet tiivistetään (hash) päivittäin vaihtuvalla suolalla (salt), raa’at IP-osoitteet eivät koskaan päädy tietokantaan D1.
  • Dashboard: Mini-kaaviokortti (SVG, ei kaaviokirjastoa) osoitteessa /dashboard/dpp/:dppId, jossa on 30 päivän pylväät + Top 3 -erittelyt. Tyhjä tila (empty state) heti, kun DPP on julkaistu mutta sillä ei ole vielä skannauksia.

2026-04 · Reaaliaikainen EU-vaatimustenmukaisuussimulaattori (Q3.3.7)

  • Uutta: POST /v1/dpp/:id/validate-update — simuloi osittaisia päivityksiä tilattomasti (stateless) (tila, markkinaluettelo, …) ilman tallennusta. Vastaus sisältää kentät eu_compliance + preview.changed_fields.
  • Dashboard: Simulaattorikortti DPP-yksityiskohdissa (/dashboard/dpp/:dppId) — pillerit (chips) arvoille DE/AT/FR/IT/ES/NL + mukautettu, tilan pudotusvalikko, Preview EU impact / Save changes / Reset. Ei-blokkaava Remix-kirjaston useFetcher-kutsun kautta.
  • Vankistus: Ulkoistetut simulaattorin apufunktiot (readUpdatePatchFromForm, marketCountriesKey) + 18 uutta yksikkötestiä; bugikorjaus: yksittäinen ei-ISO-syöte ei enää tyhjennä markkinaluetteloa.

2026-04 · Reaaliaikainen EU-vaatimustenmukaisuuden esikatselu luontilomakkeessa (Q3.3.6)

  • Muuttunut: POST /v1/dpp/validate palauttaa lisäksi kentän eu_compliance — sama validaattori kuin GET /v1/dpp/:id/eu-compliance, tilattomasti ennen tallennusta.
  • Dashboard: Esikatselu olemassa olevan validointipaneelin alapuolella + uusi Save-Guard-banneri ennen lähetyspainikkeita, jos virheitä/varoituksia on avoinna (i18n-monikkomuodot DE/EN).

2026-04 · EU-validaattori + tekstiilikäyttöliittymä (Q3.3.4 + Q3.3.5)

  • Uutta: EU-vaatimustenmukaisuusvalidaattori, jossa on 5 tekstiilisääntöä (TEXTILE_AGEC_REQUIRED, TEXTILE_MICROPLASTICS_CONSISTENCY, TEXTILE_SVHC_THRESHOLD, TEXTILE_GREENWASHING, TEXTILE_ESPR_READY).
  • Uutta: GET /v1/dpp/:id/eu-compliance, joka palauttaa kentät compliant / espr_ready / issues[] / summary.
  • Dashboard: EU-vaatimustenmukaisuusosio (EU-Compliance) DPP-yksityiskohdissa (yhteenvetolaatat, ryhmitellyt ongelmakortit, ESPR-Ready-merkki ylätunnisteessa).

2026-04 · Tekstiili-DPP-skeema (Q3.3.1–Q3.3.3)

  • Uutta: Kategoria textile ja lakisääteinen AGEC-ketju (kudonta/neulonta → värjäys/painatus → vaatteen valmistus), kuitukohtainen origin_country + recycled_pct, svhc_substances[], ESPR-opt-in (PEF, elinkaari, kierrätettävyys).
  • Uutta: Peruskenttä market_countries: string[] (ISO 3166-1 alpha-2) kaikissa DPP-kategorioissa — ohjaa Ranska-kohtaisia AGEC-sääntöjä ja ranskankielistä pakollista kuluttajailmoitusta.
  • Uutta: Kuluttajille suunnattu HTML-malli, jossa on AGEC-mikromuovivaroituslaatikko, 3-vaiheinen alkuperäketju (lippupillerit), SVHC-luettelo sekä kestävyys- ja kierrätettävyysosiot.
  • Migraatio: 0010_dpp_market_countries (D1).

2026-04 · DPP-massatuonti (Q3.2.1–Q3.2.5)

  • Uutta: POST /v1/dpp/import hyväksyy CSV- ja XLSX-tiedostot (Worker-yhteensopiva SheetJS xlsx -kirjaston kautta, ~283 kt:n gzip-paketti).
  • Skaalautuva: tilaustasoon perustuva raja (Free 100 → Enterprise 10k) + paloiteltu db.batch() 100 erissä + 5 megatavun pyynnön koon (body) raja.
  • Uutta: Virheraportti CSV-muodossa 201-vastauksen errors_csv-kentässä; GET /v1/dpp/import/templates/:category?format=csv|xlsx palauttaa valmiit mallit akulle ja tekstiilille.
  • Dashboard: Vedä ja pudota -lataus (drag-and-drop) osoitteessa /dashboard/dpp/import mallipohjavälityspalvelimen (template proxy) ja upotetun CSV-latauksen kanssa.

Ei-rikkovat muutokset — LTS-laajennukset

Kaikki edellä mainitut muutokset ovat lisääviä (additive):

  • Nykyiset POST /v1/dpp/validate-asiakkaat ohittavat uuden eu_compliance-kentän ilman muutoksia.
  • Nykyiset battery-työvoot säilyvät muuttumattomina.
  • market_countries on valinnainen ja sen oletusarvo on [].

Katso rikkovien muutosten käytäntö (breaking changes) sivulta API-versiointi.