Qual è la risposta del codice di stato HTTP appropriata per una richiesta generale non riuscita (non un errore)?

Sto creando un’API RESTful che elabora un numero di interazioni utente, incluso l’inserimento di ordini tramite carte di credito memorizzate.

In caso di un ordine riuscito, restituisco un 200 OK e nel caso in cui la richiesta di ordine non sia valida o non valida, restituisco una richiesta non valida di 400. Ma cosa dovrei restituire se c’è un problema durante l’elaborazione effettiva dell’ordine?

  1. Client POSTS ordina al server per una risorsa utente. Se l’utente non esiste, viene restituito 404 non trovato.
  2. Il formato dell’ordine e le informazioni sono convalidati. Se non è valido, viene restituita 400 Richiesta non valida.
  3. L’ordine è processato. Se l’ordine ha esito positivo, viene restituito un 201 creato per l’ordine. Se si verifica un errore imprevisto, viene restituito un errore di 500 server.

L’ultimo passaggio è il problema: cosa restituisco se l’ordine non viene completato per altri motivi? I possibili scenari potrebbero includere:

  • Il prodotto è esaurito
  • Raggiunto il limite massimo di ordini dell’utente
  • Fallimento della transazione con carta di credito (fondi insufficienti, ecc.)

Questo non sembra appropriato per un 400 o un 500. Se potessi vederlo come un 400 se non c’è un codice migliore, la richiesta non era valida secondo le regole aziendali. Semplicemente non sembra accurato.

Modifica: trovato anche questa discussione esistente sullo stesso argomento. Tutte le risposte sembrano puntare a utilizzare i codici di stato per questo tipo di violazione, con alcune discussioni tra l’utilizzo di 400, 409 o l’estensione 422.

    Dovresti usare 400 per le regole aziendali. Non restituire 2xx se l’ordine non è stato accettato. HTTP è un protocollo applicativo, non dimenticarlo mai. Se restituisci 2xx il cliente può assumere che l’ordine è stato accettato, indipendentemente dalle informazioni che hai inviato nel corpo.


    Dal ricettario dei servizi Web RESTful :

    Un errore comune riscontrato da alcuni servizi Web consiste nel restituire un codice di stato che riflette il successo (codici di stato da 200 a 206 e da 300 a 307), ma include un corpo di messaggio che descrive una condizione di errore. Ciò impedisce al software che riconosce HTTP di rilevare errori. Ad esempio, una cache la memorizzerà come risposta di successo e la servirà per i client successivi anche quando i client potrebbero essere in grado di effettuare una richiesta corretta.

    Lascerò a te decidere tra 4xx e 5xx, ma dovresti usare un codice di stato di errore.

    È necessario utilizzare 4xx per un errore del client se il client può modificare la richiesta per aggirare l’errore. Usa un 5xx per un errore del server che il client non può davvero aggirare.

    Il prodotto esaurito sarebbe un errore del server. Il client non può modificare la richiesta in alcun modo per aggirare l’errore. Potresti passare a un altro prodotto ma non sarebbe una nuova richiesta?

    Il limite massimo di ordini dell’utente raggiunto è anche un errore del server. Nulla che il client possa fare per aggirare quell’errore.

    L’errore di transazione con carta di credito sarebbe un errore del cliente. Il client potrebbe inviare nuovamente la richiesta con un metodo di pagamento diverso o un numero di carta di credito per aggirare l’errore.

    Tipo di errore:

    4×× Client Error 

    Codice di errore:

     422 Unprocessable Entity 

    Il server comprende il tipo di contenuto dell’ quadro di richiesta (quindi un codice di stato del tipo di supporto non supportato 415 è inappropriato) e la syntax dell’ quadro di richiesta è corretta (quindi un codice di stato 400 Richiesta non valido) ma non è stato in grado di elaborare il contenuto Istruzioni.

    Ad esempio, questa condizione di errore può verificarsi se un corpo di richiesta XML contiene istruzioni XML ben formate (vale a dire sintatticamente corrette), ma semanticamente errate.

    https://httpstatuses.com/422

    So che questa domanda è vecchia, ma oggi mi è venuta la stessa domanda. Se il mio utente ha esaurito i crediti, quale codice di stato deve restituire la mia API REST?

    Tendo ad inclinarmi verso 402 Payment Required :

    Secondo Wikipedia :

    Riservato per uso futuro. L’intenzione originale era che questo codice potesse essere usato come parte di una qualche forma di denaro digitale o schema di micropagamenti, ma ciò non è accaduto e questo codice non viene solitamente usato. L’API di Google Developers utilizza questo stato se un determinato sviluppatore ha superato il limite giornaliero per le richieste.

    E infatti lo fanno :

    PAYMENT_REQUIRED (402)

    • È stato raggiunto un limite di budget giornaliero impostato dallo sviluppatore.
    • L’operazione richiesta richiede più risorse di quelle consentite dalla quota. Il pagamento è richiesto per completare l’operazione.
    • L’operazione richiesta richiede un qualche tipo di pagamento da parte dell’utente autenticato.

    Non credo che 400 possano essere usati per tutti gli scenari di business. Può essere utilizzato per la convalida dei dati di base. Oltre a questo, potremmo avere difficoltà nel tempo ad integrare altre logiche di business in questo codice di errore. L’errore gestito da questo sono principalmente gli errori di progettazione che lo sviluppatore incontrerà probabilmente durante la codifica del client.

    Supponiamo che tutti i parametri siano corretti e diciamo che stiamo passando il numero dell’account utente nella richiesta.

    Quindi la richiesta non è più una ctriggers richiesta, il server è in grado di accettare la richiesta. Ma ora si rifiuta di completare la richiesta sulla base di nuove informazioni disponibili che è – l’account non ha un equilibrio sufficiente.

    Suggerirei di utilizzare 403 con il messaggio di errore appropriato in questi scenari.

    Altro codice di errore ansible potrebbe essere 409 conflitto. Ma questo è usato in scenari in cui la risorsa è in uno stato coerente.

    Vado con 406 Not Acceptable .

    Ecco una lista 4xx:

     const HTTP_BAD_REQUEST = 400; const HTTP_UNAUTHORIZED = 401; const HTTP_PAYMENT_REQUIRED = 402; const HTTP_FORBIDDEN = 403; const HTTP_NOT_FOUND = 404; const HTTP_METHOD_NOT_ALLOWED = 405; const HTTP_NOT_ACCEPTABLE = 406; const HTTP_PROXY_AUTHENTICATION_REQUIRED = 407; const HTTP_REQUEST_TIMEOUT = 408; const HTTP_CONFLICT = 409; const HTTP_GONE = 410; const HTTP_LENGTH_REQUIRED = 411; const HTTP_PRECONDITION_FAILED = 412; const HTTP_REQUEST_ENTITY_TOO_LARGE = 413; const HTTP_REQUEST_URI_TOO_LONG = 414; const HTTP_UNSUPPORTED_MEDIA_TYPE = 415; const HTTP_REQUESTED_RANGE_NOT_SATISFIABLE = 416; const HTTP_EXPECTATION_FAILED = 417; const HTTP_I_AM_A_TEAPOT = 418; // RFC2324 const HTTP_MISDIRECTED_REQUEST = 421; // RFC7540 const HTTP_UNPROCESSABLE_ENTITY = 422; // RFC4918 const HTTP_LOCKED = 423; // RFC4918 const HTTP_FAILED_DEPENDENCY = 424; // RFC4918 const HTTP_RESERVED_FOR_WEBDAV_ADVANCED_COLLECTIONS_EXPIRED_PROPOSAL = 425; // RFC2817 const HTTP_UPGRADE_REQUIRED = 426; // RFC2817 const HTTP_PRECONDITION_REQUIRED = 428; // RFC6585 const HTTP_TOO_MANY_REQUESTS = 429; // RFC6585