Introduzione
Nel panorama dello sviluppo backend moderno, la scelta tra REST API e GraphQL è una delle decisioni architetturali più importanti. Entrambe hanno i loro punti di forza, ma servono casi d'uso diversi.
In questo articolo, basandomi sulla mia esperienza con entrambe le tecnologie in produzione, ti guiderò attraverso un confronto pratico per aiutarti a scegliere la soluzione migliore per il tuo progetto.
REST API: Il Veterano Affidabile
REST (Representational State Transfer) è un'architettura per API web che utilizza i metodi HTTP standard. È lo standard de facto da oltre 20 anni.
Caratteristiche Principali di REST
- Risorse come Endpoint: Ogni risorsa ha il suo URL unico
- Metodi HTTP Standard: GET, POST, PUT, DELETE, PATCH
- Stateless: Ogni richiesta contiene tutte le informazioni necessarie
- Caching Nativo: Supporto HTTP caching integrato
- Standardizzato: Pattern e convenzioni ben consolidati
Vantaggi REST
- Semplicità e familiarità
- Caching HTTP nativo
- Ottime performance per operazioni CRUD semplici
- Tool e debugging consolidati
- Supporto universale
Svantaggi REST
- Over-fetching (dati non necessari)
- Under-fetching (multiple richieste)
- Versionamento API complesso
- Difficoltà con relazioni nested
- Endpoint proliferano rapidamente
Esempio REST API: E-Commerce
// REST API Endpoints
GET /api/users/:id // Get user
GET /api/users/:id/orders // Get user orders
GET /api/orders/:id // Get single order
GET /api/orders/:id/items // Get order items
GET /api/products/:id // Get product details
// Esempio: Server Node.js con Express
const express = require('express');
const app = express();
// Get user with orders
app.get('/api/users/:id', async (req, res) => {
const user = await User.findById(req.params.id);
res.json(user);
});
// Get user orders
app.get('/api/users/:id/orders', async (req, res) => {
const orders = await Order.find({ userId: req.params.id });
res.json(orders);
});
// PROBLEMA: Per ottenere user + orders + order items
// servono 3+ chiamate API separate!
// 1. GET /api/users/123
// 2. GET /api/users/123/orders
// 3. GET /api/orders/456/items (per ogni ordine)
GraphQL: Il Nuovo Standard Flessibile
GraphQL è un query language per API sviluppato da Facebook nel 2015. Permette ai client di richiedere esattamente i dati di cui hanno bisogno.
Caratteristiche Principali di GraphQL
- Single Endpoint: Un solo endpoint per tutte le operazioni
- Query Dichiarative: Il client specifica esattamente cosa vuole
- Strongly Typed: Schema type system completo
- Real-time: Subscriptions per dati live
- Introspection: API auto-documentata
Vantaggi GraphQL
- Fetch preciso dei dati necessari
- Singola richiesta per dati complessi
- No versionamento API
- Schema fortemente tipizzato
- Ottimo per frontend development
- Real-time subscriptions
Svantaggi GraphQL
- Curva di apprendimento più ripida
- Caching più complesso
- Performance imprevedibili con query complesse
- Overhead per operazioni semplici
- File upload più complicato
Esempio GraphQL: Stessa Applicazione E-Commerce
# Schema GraphQL
type User {
id: ID!
name: String!
email: String!
orders: [Order!]!
}
type Order {
id: ID!
total: Float!
status: String!
items: [OrderItem!]!
createdAt: DateTime!
}
type OrderItem {
id: ID!
quantity: Int!
price: Float!
product: Product!
}
type Product {
id: ID!
name: String!
price: Float!
description: String
}
# Query per ottenere tutto in UNA richiesta!
query GetUserWithOrders($userId: ID!) {
user(id: $userId) {
id
name
email
orders {
id
total
status
items {
quantity
price
product {
name
description
}
}
}
}
}
Confronto Diretto: REST vs GraphQL
| Caratteristica | REST | GraphQL |
|---|---|---|
| Endpoint | Multipli per risorsa | Singolo endpoint |
| Data Fetching | Fixed data structure | Client specifica esattamente |
| Over/Under-fetching | Comune | Eliminato |
| Versionamento | /v1/, /v2/ necessario | Deprecation, no versioni |
| Caching | HTTP caching nativo | Richiede strategie custom |
| Real-time | WebSockets/SSE separati | Subscriptions native |
| Learning Curve | Bassa | Media-Alta |
| Performance | Ottima per CRUD semplici | Ottima per query complesse |
Hasura: GraphQL Instantaneo su PostgreSQL
Hasura è un engine GraphQL che genera automaticamente API GraphQL dal tuo database PostgreSQL. Nella mia esperienza, ha accelerato lo sviluppo del 70%.
Vantaggi di Hasura
- Zero Code: GraphQL API generata automaticamente
- Real-time: Subscriptions out-of-the-box
- Role-based Access: Sistema di permessi granulare
- Remote Schemas: Integra API esterne
- Event Triggers: Business logic su eventi DB
- Performance: Query ottimizzate automaticamente
Setup Hasura in 5 Minuti
# docker-compose.yml
version: '3.8'
services:
postgres:
image: postgres:15
environment:
POSTGRES_PASSWORD: password
volumes:
- postgres_data:/var/lib/postgresql/data
hasura:
image: hasura/graphql-engine:latest
ports:
- "8080:8080"
environment:
HASURA_GRAPHQL_DATABASE_URL: postgres://postgres:password@postgres:5432/postgres
HASURA_GRAPHQL_ENABLE_CONSOLE: "true"
HASURA_GRAPHQL_ADMIN_SECRET: myadminsecret
depends_on:
- postgres
volumes:
postgres_data:
# Avvia Hasura
docker-compose up -d
# Vai su http://localhost:8080
# Console GraphQL pronta all'uso!
# Crea tabelle via UI o migrations
# API GraphQL generata automaticamente
Quando Usare REST
- Hai operazioni CRUD semplici e dirette
- Il caching è prioritario (CDN, browser cache)
- Il team ha poca esperienza con GraphQL
- Hai bisogno di HTTP verbs semantici (GET, POST, PUT, DELETE)
- Stai costruendo API pubbliche per terze parti
- Il progetto è semplice e lo schema è stabile
- Hai bisogno di file upload/download pesanti
Quando Usare GraphQL
- Hai relazioni complesse tra entità
- Il frontend necessita flessibilità nei dati
- Vuoi ridurre numero di richieste HTTP
- Hai bisogno di real-time data (subscriptions)
- Stai costruendo app mobile (bandwidth limitato)
- Vuoi API auto-documentata e type-safe
- Il team frontend e backend lavorano in parallelo
L'Approccio Ibrido
Non devi scegliere solo uno! Molte applicazioni moderne usano entrambi:
- GraphQL per operazioni di lettura complesse e UI interattive
- REST per upload file, webhook, public API
- gRPC per comunicazione interna microservizi
Esempio Architettura Ibrida
// API Gateway con Express
const express = require('express');
const { ApolloServer } = require('apollo-server-express');
const app = express();
// GraphQL per query complesse
const server = new ApolloServer({
typeDefs,
resolvers,
});
server.applyMiddleware({ app, path: '/graphql' });
// REST per file upload
app.post('/api/upload', upload.single('file'), (req, res) => {
// Handle file upload
res.json({ url: req.file.path });
});
// REST per webhook esterni
app.post('/api/webhooks/stripe', (req, res) => {
// Handle Stripe webhook
res.sendStatus(200);
});
app.listen(4000);
La Mia Esperienza in Produzione
Progetto 1: Dashboard Analytics con Hasura + GraphQL
Per una fintech, ho implementato una dashboard real-time con Hasura:
- Query complesse con JOIN multipli risolte in una richiesta
- Real-time subscriptions per aggiornamenti live
- Sviluppo 70% più veloce rispetto a REST tradizionale
- Frontend poteva iterare senza modifiche backend
Progetto 2: API Pubblica con REST
Per un e-commerce, ho progettato REST API pubbliche:
- Semplicità per integrazioni terze parti
- Caching CDN out-of-the-box
- Documentazione Swagger familiare
- Rate limiting per endpoint specifici
Conclusioni e Raccomandazioni
La scelta tra REST e GraphQL dipende dal tuo caso d'uso specifico:
Inizia con GraphQL + Hasura se:
- Stai costruendo una nuova applicazione
- Hai relazioni complesse tra entità
- Vuoi velocizzare lo sviluppo
Usa REST per:
- API pubbliche e webhook
- File upload/download
- Quando semplicità > flessibilità
Risorse Utili
- GraphQL Official:
https://graphql.org/ - Hasura Documentation:
https://hasura.io/docs/ - Apollo GraphQL:
https://www.apollographql.com/ - REST API Best Practices (Microsoft)
Hai bisogno di aiuto?
Se stai valutando quale tecnologia usare per il tuo progetto, o se vuoi migrare da REST a GraphQL (o viceversa), contattami per una consulenza. Ho implementato entrambe le soluzioni in produzione e posso guidarti nella scelta giusta.