GraphQL vs REST: Qual a Melhor Escolha para sua Próxima API em Laravel?

GraphQL vs REST

A escolha entre GraphQL e REST é uma das decisões de arquitetura mais importantes que você tomará no início de um projeto em Laravel.

Ambos têm o mesmo objetivo—permitir que seu frontend (seja um app mobile ou um site em React/Vue) converse com seu backend (Laravel)—mas eles fazem isso de maneiras fundamentalmente diferentes.

Vamos quebrar essa decisão com uma didática clara e exemplos práticos focados no Laravel.


O Padrão Estabelecido: Entendendo o REST

O que é REST (REpresentational State Transfer)?

Pense no REST como um cardápio de restaurante com “pratos feitos” (combos). O restaurante (API) decide exatamente o que vem em cada prato (endpoint).

O REST é um estilo arquitetural que usa os métodos HTTP (GET, POST, PUT, DELETE) e URLs (endpoints) para definir operações. Cada “coisa” no seu aplicativo (um usuário, um post, um comentário) é um recurso.

  • Quer um usuário? GET /users/1
  • Quer os posts desse usuário? GET /users/1/posts
  • Quer criar um post? POST /posts

O servidor define a estrutura da resposta. Se você pedir /users/1, o servidor decide que vai lhe enviar o id, name, email, created_at e updated_at, quer você precise de todos eles ou não.

Exemplo Prático: REST em Laravel (com API Resources)

O Laravel é fantástico para construir APIs REST. Ele foi praticamente feito para isso. Você usa rotas, controladores e, o mais importante, API Resources.

1. A Rota (routes/api.php):

PHP

use App\Http\Controllers\UserController;

// Rota para buscar um usuário específico
Route::get('/users/{id}', [UserController::class, 'show']);

2. O Controller (app/Http/Controllers/UserController.php):

Aqui, usamos um UserResource para formatar a resposta. Esta é a melhor prática em Laravel.

PHP

namespace App\Http\Controllers;

use App\Models\User;
use App\Http\Resources\UserResource;

class UserController extends Controller
{
    public function show(string $id)
    {
        $user = User::findOrFail($id);
        
        // O UserResource formata o JSON de saída
        return new UserResource($user);
    }
}

3. A Resposta (JSON):

O UserResource define que a resposta será assim:

JSON

{
  "data": {
    "id": 1,
    "name": "João Silva",
    "email": "joao@exemplo.com",
    "data_de_cadastro": "2025-11-10"
  }
}
Prós e Contras do REST
  • Prós:
    • Simples e Madura: É fácil de entender e existe há décadas.
    • Caching Fácil: As URLs (como GET /users/1) são fáceis de armazenar em cache.
    • Ecossistema Laravel: O Laravel tem ferramentas nativas perfeitas (Eloquent, API Resources, Sanctum) para REST.
  • Contras:
    • Over-fetching (Excesso de dados): O GET /users/1 pode trazer 50 campos, mas seu app mobile só precisava do name. Isso é um desperdício de banda.
    • Under-fetching (Falta de dados): Você precisa da info do usuário E seus 10 últimos posts. Você tem que fazer duas requisições: GET /users/1 e depois GET /users/1/posts. Isso é lento.

A Alternativa Moderna: Conhecendo o GraphQL

O que é GraphQL?

Se o REST é um cardápio de “pratos feitos”, o GraphQL é um buffet self-service. Você (o cliente) pega um prato e escolhe exatamente o que quer e a quantidade de cada coisa.

O GraphQL é uma linguagem de consulta (Query Language) para APIs. Em vez de múltiplos endpoints, o GraphQL geralmente expõe um único endpoint (ex: /graphql).

O cliente envia uma “query” (consulta) em formato de texto, descrevendo quais dados ele precisa. O servidor interpreta essa query, busca os dados e retorna um JSON que espelha exatamente a estrutura da query.

Exemplo Prático: GraphQL em Laravel (com Lighthouse)

O Laravel não vem com suporte nativo para GraphQL, mas a comunidade tem um pacote incrível chamado Lighthouse. Ele permite que você defina sua API usando a própria linguagem do GraphQL (arquivos .graphql), o que é muito elegante.

1. O Schema (resources/graphql/schema.graphql):

Você primeiro define seus “tipos” e “consultas” disponíveis.

GraphQL

# Define como é um usuário
type User {
  id: ID!
  name: String!
  email: String!
  posts: [Post!]! # Um usuário pode ter uma lista de posts
}

# Define como é um post
type Post {
  id: ID!
  title: String!
  body: String
}

# Define as "portas de entrada" da API
type Query {
  # Permite buscar um usuário pelo ID
  user(id: ID!): User @find(model: "App\\Models\\User")

  # Permite buscar todos os posts
  posts: [Post!]! @all(model: "App\\Models\\Post")
}

(Note os @find e @all – são diretivas do Lighthouse que magicamente conectam seu schema aos seus Models Eloquent!)

2. A Requisição (Query) do Cliente:

Agora, o frontend (em vez de fazer 2 requests REST) faz 1 query GraphQL para o endpoint /graphql:

GraphQL

# Eu quero o usuário de ID 1, mas só me traga o nome.
# E desse usuário, traga os títulos dos 3 últimos posts dele.
query {
  user(id: 1) {
    name
    posts(first: 3) {
      title
    }
  }
}

3. A Resposta (JSON):

O servidor responde com um JSON que imita perfeitamente a forma da query:

JSON

{
  "data": {
    "user": {
      "name": "João Silva",
      "posts": [
        { "title": "Meu primeiro post" },
        { "title": "Laravel é demais" },
        { "title": "GraphQL e Laravel" }
      ]
    }
  }
}

Note que o email do usuário e o body dos posts não vieram. Zero over-fetching! E tudo em uma só requisição. Zero under-fetching!

Prós e Contras do GraphQL
  • Prós:
    • Resolve Over/Under-fetching: O cliente tem controle total e pega exatamente o que precisa em uma só viagem.
    • Fortemente Tipado: O schema é um contrato claro entre frontend e backend.
    • Ideal para Frontends Modernos: Perfeito para apps mobile ou SPAs (React/Vue) que têm necessidades de dados complexas e variáveis.
  • Contras:
    • Curva de Aprendizado: É mais complexo de configurar inicialmente que o REST.
    • Caching Complicado: Como todas as queries vão para o POST /graphql, você perde o cache HTTP simples de URLs.
    • Dependência de Pacotes: No Laravel, você precisa de pacotes como o Lighthouse ou Rebing/GraphQL-Laravel.

O Veredito: Qual Devo Escolher para Meu Projeto Laravel?

Como um bom especialista, a resposta não é “um é melhor”, mas sim “depende do seu caso de uso”.

Escolha REST se…
  • …você está construindo uma API pública simples (ex: API do tempo, API de cotações) onde os recursos são bem definidos.
  • …seu projeto é um CRUD (Create, Read, Update, Delete) clássico.
  • …sua equipe já é altamente proficiente em REST e o tempo de entrega é crítico.
  • …caching HTTP simples é uma prioridade alta para você.
  • …você quer usar o máximo do que o Laravel oferece nativamente (API Resources, Sanctum) sem adicionar novas dependências.
Escolha GraphQL se…
  • …você está servindo múltiplos clientes (ex: um app iOS, um app Android e um site React) e cada um precisa de um conjunto diferente de dados.
  • …seu frontend precisa de flexibilidade para pedir dados complexos e aninhados sem sobrecarregar o backend.
  • …você quer evitar dezenas de endpoints customizados (ex: /user-with-posts, /user-with-posts-and-comments).
  • …a largura de banda é uma preocupação (especialmente em apps mobile) e o over-fetching do REST é um problema real.
  • …você está construindo um app onde os dados são muito interligados (como uma rede social ou um painel de BI).

Resumo Final

Para a maioria dos projetos Laravel “padrão”, começar com REST é mais rápido, mais simples e usa todo o poder nativo do framework.

Para projetos grandes e complexos, especialmente aqueles com frontends modernos desacoplados (SPAs, Mobile), investir o tempo para aprender GraphQL e Lighthouse no Laravel pode economizar centenas de horas de desenvolvimento no futuro, eliminando a necessidade de criar e manter dezenas de endpoints REST customizados.

Espero que esta explicação completa e com a formatação correta tenha ajudado a clarear sua decisão!

Deixe um comentário

O seu endereço de e-mail não será publicado. Campos obrigatórios são marcados com *

Rolar para cima