alltools.one
API
2025-06-05
7 min
alltools.one Team
APIRESTJSONResponse FormatBest Practices

Formati di Risposta API: Best Practice per API Coerenti

Le risposte API incoerenti sono una delle principali lamentele degli sviluppatori frontend. Quando ogni endpoint restituisce dati in una forma diversa, il codice client diventa pieno di casi speciali. Un formato di risposta coerente migliora l'esperienza dello sviluppatore, riduce i bug e rende la tua API auto-documentante.

L'Envelope di Risposta

Avvolgi ogni risposta in una struttura coerente:

Successo (Risorsa Singola)

{
  "data": {
    "id": "user_123",
    "name": "Alice",
    "email": "alice@example.com",
    "createdAt": "2024-01-15T10:30:00Z"
  },
  "meta": {
    "requestId": "req_abc123"
  }
}

Successo (Collezione)

{
  "data": [
    { "id": "user_123", "name": "Alice" },
    { "id": "user_456", "name": "Bob" }
  ],
  "meta": {
    "total": 142,
    "page": 1,
    "perPage": 20,
    "requestId": "req_def456"
  }
}

Errore

{
  "error": {
    "code": "VALIDATION_ERROR",
    "message": "Request validation failed",
    "details": [
      { "field": "email", "message": "Invalid email format" }
    ]
  },
  "meta": {
    "requestId": "req_ghi789"
  }
}

Il principio chiave: i client controllano sempre data o error al livello superiore. Non mescolare mai dati di successo e informazioni di errore nella stessa risposta.

Valida il formato della tua risposta con il nostro Validatore JSON.

Codici di Stato HTTP

Usa i codici di stato correttamente — sono la prima cosa che i client controllano:

Codici di Successo

CodiceQuando
200 OKGET riuscito, PUT/PATCH riuscito
201 CreatedPOST che ha creato una risorsa
204 No ContentDELETE riuscito (nessun body)

Codici di Errore Client

CodiceQuando
400 Bad RequestSintassi della richiesta malformata
401 UnauthorizedAutenticazione mancante o non valida
403 ForbiddenAutenticato ma non autorizzato
404 Not FoundLa risorsa non esiste
409 ConflictConflitto di stato della risorsa (duplicato)
422 UnprocessableSintassi valida ma errori semantici
429 Too Many RequestsLimite di frequenza superato

Codici di Errore Server

CodiceQuando
500 Internal Server ErrorErrore server inatteso
502 Bad GatewayErrore servizio upstream
503 Service UnavailableSovraccarico temporaneo o manutenzione

Design della Risposta di Errore

Buone risposte di errore aiutano gli sviluppatori a fare debug rapidamente:

{
  "error": {
    "code": "RESOURCE_NOT_FOUND",
    "message": "User with ID 'user_999' not found",
    "details": [],
    "documentationUrl": "https://api.example.com/docs/errors#RESOURCE_NOT_FOUND"
  },
  "meta": {
    "requestId": "req_xyz789",
    "timestamp": "2024-01-15T10:30:00Z"
  }
}

Regole:

  • code è leggibile dalla macchina (stringa costante, non stato HTTP)
  • message è leggibile dall'uomo (può cambiare senza rompere i client)
  • details fornisce errori a livello di campo per i fallimenti di validazione
  • requestId permette al team di supporto di tracciare la richiesta nei log

Pattern di Paginazione

Basata su Offset

Semplice e supporta il salto a pagine arbitrarie:

{
  "data": ["..."],
  "meta": {
    "page": 2,
    "perPage": 20,
    "total": 142,
    "totalPages": 8
  },
  "links": {
    "first": "/api/users?page=1&per_page=20",
    "prev": "/api/users?page=1&per_page=20",
    "next": "/api/users?page=3&per_page=20",
    "last": "/api/users?page=8&per_page=20"
  }
}

Basata su Cursore

Migliore per dati in tempo reale e grandi dataset:

{
  "data": ["..."],
  "meta": {
    "hasNext": true,
    "hasPrev": true
  },
  "links": {
    "next": "/api/users?cursor=eyJpZCI6MTQzfQ&limit=20",
    "prev": "/api/users?cursor=eyJpZCI6MTIzfQ&limit=20&direction=prev"
  }
}

Data e Ora

Usa sempre ISO 8601 con informazione sul fuso orario:

{
  "createdAt": "2024-01-15T10:30:00Z",
  "updatedAt": "2024-01-15T14:22:33+00:00",
  "expiresAt": "2024-12-31T23:59:59Z"
}

Non usare mai:

  • Timestamp Unix (ambigui: secondi o millisecondi?)
  • Date locali senza fuso orario
  • Formati personalizzati come MM/GG/AAAA

Per approfondire la gestione dei timestamp, consulta la nostra guida ai Timestamp Unix.

Null vs Campi Assenti

Due approcci comuni:

Includi con null (esplicito):

{ "name": "Alice", "avatar": null, "bio": null }

Ometti i campi assenti (sparso):

{ "name": "Alice" }

Raccomandazione: Sii coerente all'interno della tua API. I null espliciti sono migliori per i linguaggi tipizzati (i client sanno che il campo esiste). Lo stile sparso è migliore per ambienti con larghezza di banda limitata.

Versionamento delle Risposte

Quando il formato della risposta cambia, versiona la tua API:

GET /api/v2/users/123

Modifiche che richiedono versionamento:

  • Rimuovere un campo
  • Cambiare il tipo di un campo
  • Rinominare un campo
  • Cambiare la struttura dell'envelope di risposta

Modifiche non distruttive (sicure senza versionamento):

  • Aggiungere nuovi campi
  • Aggiungere nuovi endpoint
  • Aggiungere nuovi valori enum

FAQ

Dovrei avvolgere le risposte di successo in una chiave data o restituire la risorsa direttamente?

Usare un wrapper data fornisce una struttura coerente per tutte le risposte e lascia spazio per metadati, paginazione e link insieme ai dati. Restituire la risorsa direttamente è più semplice per endpoint a risorsa singola. La maggior parte delle API moderne usa l'approccio wrapper per coerenza.

Come dovrei gestire i fallimenti parziali nelle operazioni batch?

Restituisci 200 con una risposta che include sia successi che fallimenti nell'oggetto data. Usare 207 Multi-Status (WebDAV) è un'altra opzione ma meno comunemente usata nelle API REST.

Risorse Correlate

Published on 2025-06-05
API Response Formats: Best Practices for Consistent APIs | alltools.one