Virheet
Sursa kertoo HTTP-tilakoodilla, onnistuiko pyyntö, ja pysyvällä virhekoodilla, miksi se ei onnistunut. Jokaisella virhevastauksella on sama rakenne:
{
"detail": "the cursor is malformed or was issued for different filters",
"error": {
"code": "api.cursor_invalid",
"message": "the cursor is malformed or was issued for different filters",
"details": {"parameter": "cursor"},
"request_id": "01JB7Q2M4X9V3K8T5N6P0R1S2A",
"doc_url": "https://developers.sursa.com/errors/api.cursor_invalid"
}
}
| Kenttä | Merkitys |
|---|---|
error.code | Pysyvä koodi muodossa <area>.<reason>. Haarauta koodisi toiminta sen mukaan. |
error.message | Luettava englanninkielinen selitys. Sen sanamuoto voi muuttua milloin tahansa; älä jäsennä sitä. |
error.details | Jäsennellyt tiedot virheestä, kuten parametri, raja tai milloin kannattaa yrittää uudelleen. Sen kentät riippuvat koodista. |
error.request_id | Tämän pyynnön tunnus, sama kuin X-Request-Id-vastausotsakkeessa. |
error.doc_url | Tämän koodin sivu tässä portaalissa. |
detail | Virheen aiempi muoto, joka on säilytetty olemassa olevia integraatioita varten. Uuden koodin kannattaa lukea error. |
Jokaisella koodilla on oma sivunsa kohdassa Virhekoodit: sen HTTP-tila, details-kentät ja päätepisteet,
jotka palauttavat sen. API-viitteen jokaisen päätepisteen sivulla luetellaan koodit, jotka kyseinen
päätepiste voi palauttaa.
HTTP-tilat
| Tila | Merkitys |
|---|---|
200, 201, 202, 204 | Pyyntö onnistui. 202 tarkoittaa, että pyyntö on hyväksytty ja sen käsittely on vielä kesken. |
400 | Pyyntö on muodostettu virheellisesti: virheellinen parametri, kursori, metadata tai Idempotency-Key. Korjaa pyyntö. |
401 | Kelvollista avainta ei ole. Ks. Todennus. |
402 | Organisaation paketin raja on saavutettu, esimerkiksi korttien määrä tai tallennustila. |
403 | Avain on kelvollinen, mutta sillä ei ole lupaa tähän: rooli, käyttöalue tai paketin ominaisuus puuttuu. |
404 | Objektia ei ole olemassa, tai avain ei saa nähdä sitä. |
409 | Pyyntö on ristiriidassa nykyisen tilan kanssa: toistuva external_id, avoin synkronointi tai samalla Idempotency-Key-otsakkeella tehty pyyntö, joka on vielä käynnissä. |
410 | Objektin voimassaolo on päättynyt, kuten latauksen 24 tunnin jälkeen, tai reitti on poistettu käytöstä. |
413 | Runko tai tiedosto on liian suuri. |
415 | Tiedostotyyppiä ei tueta, tai tiedoston sisältö ei vastaa sen nimeä. |
422 | Pyyntö on muodostettu oikein, mutta se on virheellinen: kenttä puuttuu tai arvo on sallitun alueen ulkopuolella. |
429 | Liian monta pyyntöä, tai kiintiö on käytetty. Ks. Nopeusrajoitukset ja kiintiöt. |
500, 502, 503, 504 | Ongelma Sursan puolella. Yritä myöhemmin uudelleen. |
Validointivirheet
Kun vastaus on 422 ja koodi validation.failed, detail luettelee jokaisen
virheellisen kentän ja sen sijainnin:
{
"detail": [
{"loc": ["body", "title"], "msg": "String should have at least 1 character", "type": "string_too_short"}
],
"error": {"code": "validation.failed", "message": "request validation failed", "request_id": "01JB7…"}
}
Mitkä virheet kannattaa yrittää uudelleen
| Virhe | Yritetäänkö uudelleen? |
|---|---|
| Verkkovirhe tai aikakatkaisu, ei vastausta | Kyllä, samalla Idempotency-Key-otsakkeella. |
429 | Kyllä, kun Retry-After-otsakkeen ilmoittamat sekunnit ovat kuluneet. |
500, 502, 503, 504 | Kyllä, eksponentiaalisella odotuksella: 1 s, 2 s, 4 s… enintään minuuttiin asti, satunnaishajonnalla. |
409 api.idempotency_in_progress | Kyllä, Retry-After-ajan jälkeen: ensimmäinen pyyntö tällä avaimella on vielä käynnissä. |
Mikä tahansa muu 4xx | Ei. Sama pyyntö epäonnistuu uudelleen; korjaa se ensin. |
Yritä POST- ja PATCH-pyyntöjä uudelleen vain Idempotency-Key-otsakkeen kanssa,
jotta kadonneen vastauksen jälkeinen uusintayritys ei voi luoda toista objektia. GET, PUT ja DELETE ovat
turvallisia yrittää uudelleen sellaisinaan.
// Retries a request on network errors, 429 and 5xx. The same Idempotency-Key is sent on every attempt.
async function withRetries(send, attempts = 5) {
for (let attempt = 1; ; attempt++) {
let response;
try {
response = await send();
} catch (error) {
if (attempt >= attempts) throw error;
}
if (response && response.status !== 429 && response.status < 500) return response;
if (attempt >= attempts) return response;
const retryAfter = Number(response?.headers.get("Retry-After"));
const backoff = Math.min(60, 2 ** (attempt - 1)) * (0.8 + Math.random() * 0.4);
await new Promise((resolve) => setTimeout(resolve, 1000 * (retryAfter || backoff)));
}
}
const key = crypto.randomUUID();
const response = await withRetries(() =>
fetch("https://api.sursa.com/v1/cards/text", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.SURSA_API_KEY}`,
"Content-Type": "application/json",
"Idempotency-Key": key,
},
body: JSON.stringify({ title: "Refund policy", body_markdown: "Refunds take 14 days." }),
}),
);Ongelmasta ilmoittaminen
Jokaisessa vastauksessa, onnistuneessa tai epäonnistuneessa, on X-Request-Id-otsake, ja jokaisessa virheessä on
sama arvo error.request_id-kentässä. Kirjaa se lokiin oman pyyntömerkintäsi yhteyteen. Kun otat yhteyttä tukeen
jostakin pyynnöstä, lähetä sen pyyntötunnus: se johtaa suoraan kyseisen pyynnön merkintään.
Tuntemattomien koodien käsittely
Uusia virhekoodeja voi ilmestyä mihin tahansa API:n versioon. Käsittele tuntematon koodi sen HTTP-tilan mukaan:
tuntematon 4xx pyyntönä, joka ei onnistu sellaisenaan, ja tuntematon 5xx tilapäisenä ongelmana.