Every couple of years, someone declares GraphQL the future of APIs. Every couple of years, REST refuses to die. Both are still going strong in 2026 because they solve genuinely different problems. This post walks through how to choose between them — not as an ideological question, but as a concrete one based on the kind of clients, data, and team you have.
The 30-second summary
REST is a set of conventions for using HTTP. You define endpoints, each one returning a fixed shape of data. The wire format is HTTP and JSON.
GraphQL is a query language. You define a schema (types, fields, relationships), and clients send queries that ask for exactly what they want. There's typically a single endpoint that accepts arbitrary queries.
Neither is "newer" or "more modern." They're different tools for different jobs.
Where REST shines
REST is the right answer when:
- Your data shape is stable. A
/posts/123endpoint returning a post is fine forever. - Caching matters. HTTP caching (CDNs, browser cache,
ETag,Cache-Control) works out of the box for REST. With GraphQL, you generally have to build it yourself. - Your clients are heterogeneous. Server-to-server APIs, CLI tools, partners with old HTTP libraries — all of them speak REST natively.
- You want a small surface area. A REST API has a finite, listable set of endpoints. A GraphQL schema with relationships can produce essentially infinite query shapes.
In small to mid-sized projects, REST is almost always less work to ship and easier to debug.
Where GraphQL earns its weight
GraphQL is the right answer when:
- Your client genuinely needs to compose data across many entities in arbitrary combinations. A mobile app that shows a user's profile, recent posts, recent followers, and stats in a single screen — without making four round trips and fetching extra fields — is the canonical case.
- You have many different clients with different needs. Web, iOS, Android, partner integrations all consuming the same API but each wanting a different slice. GraphQL lets each client take what it needs without you maintaining custom endpoints.
- You have a strong product team that iterates quickly on UI. GraphQL can absorb a lot of UI churn without backend changes.
- You'd benefit from a typed schema as a contract between teams. The schema is genuinely useful documentation.
The over/under-fetching argument is real, but it's not always decisive. If your client needs roughly the same data shape on every screen, REST will do fine.
Where each one struggles
A fair list of pain points for both:
REST struggles with
- Over-fetching. A
/users/123endpoint returns more than the client needs because you don't want one endpoint per UI variation. - Under-fetching. Showing a user with their last five posts requires two requests, or a special endpoint that combines them.
- Versioning. Breaking changes mean either coordination or
/v2/. Nobody loves either option.
GraphQL struggles with
- Caching. HTTP caching is much harder when every request hits the same endpoint with a different query body. Solving this requires a layer (Apollo, Relay, urql) and effort.
- Authorization. Field-level auth across deeply nested queries is genuinely complex. "Can this user see this user's posts' comments' authors?" gets thorny fast.
- Performance shape. It's easy for a client to ask for a query that issues fifty database queries. The classic N+1 problem moves from "happens on a particular endpoint" to "happens anywhere in the schema."
- Server complexity. A real GraphQL server isn't a weekend project. Schema, resolvers, dataloaders, complexity limits, depth limits, persisted queries — there's a lot.
A worked example
Consider showing a user profile with their three most recent posts and the comment count on each.
REST might look like:
GET /users/123
GET /users/123/posts?limit=3
GET /posts/{id}/comments/count # for each post
Three round trips, or a custom /users/123/profile endpoint that bundles them. Both options are fine.
GraphQL might look like:
query {
user(id: "123") {
name
avatarUrl
posts(limit: 3) {
id
title
commentCount
}
}
}
One round trip, exactly the fields the UI needs, no custom endpoint. This is GraphQL at its best — provided your server can resolve commentCount efficiently for each post (with a dataloader, in this case).
What changes in production
The hype around GraphQL skips over the part where you have to operate it. Some realities:
- You need persisted queries in production. Letting clients send arbitrary queries to your server is fine for trusted clients on your team. It's a security and performance hazard for a public API.
- You need complexity limits. A
query { user { posts { author { posts { author { ... } } } } } }can take down a server. Libraries like graphql-cost-analysis exist for a reason. - You need schema management discipline. Schema changes need to be tracked, reviewed, and ideally automated — Apollo Studio, Hasura, or similar tooling helps. Without it, schemas drift and stale fields linger forever.
REST has its own production realities (idempotency keys, rate limits, retry policies), but they're more familiar to most teams.
When to use both
A surprisingly common pattern in 2026: REST for server-to-server and integrations, GraphQL for the front-end-facing API. It's not always the wrong answer.
You can also use REST 95% of the time and add a single GraphQL endpoint for the one screen that genuinely benefits from it. You don't have to commit to one religion.
A decision framework
Run through this honestly:
- Will most of your traffic be a small set of fixed-shape calls? REST.
- Do you have multiple clients with very different data needs? GraphQL.
- Is HTTP caching critical to your performance story? REST.
- Is your front-end product team faster than your backend team? GraphQL (often) helps absorb that churn.
- Is your team small and pragmatic, with no GraphQL experience? REST.
- Are you building a public API for unknown developers? REST, almost always.
Notice that none of these answers say "REST is better" or "GraphQL is better." They say which one fits your situation.
What we'd choose for a new project today
If we were starting a new web product in 2026 with one product team and a small backend, we'd build a clean REST API with:
- Cursor-based pagination
- Consistent error shapes
- A documented OpenAPI spec
- Optional response shaping via query parameters where it actually saves a round trip
We'd consider GraphQL when one of these became true:
- Multiple clients with significantly different data needs
- A persistent UI churn problem that backend changes couldn't keep up with
- A product team big enough to maintain the schema as a serious artifact
Both technologies are mature and well-supported. The wrong choice isn't catastrophic — you'll ship something fine either way. The right choice is the one whose pain points your team can absorb without bleeding velocity. Be honest about that, and you'll pick correctly more often than the average tweet thread suggests.