GraphQL vs REST vs tRPC - The 2024 Guide

Choosing Your API Strategy (Without the Hype)

“GraphQL solves all REST problems!” they said. Two years later, half switched back. Here’s what they don’t tell you.

The GraphQL Migration That Failed

We had a perfectly good REST API. New CTO arrives: “We’re moving to GraphQL. It’s the future.”

Six months later: API was slower. Frontend confused. Backend overwhelmed. We had both GraphQL AND REST (worst combo).

Why? We adopted it because it was trendy, not because we needed it.

The Truth: No “Best” API

There’s only:

  • What fits your use case
  • What your team knows
  • What problems you actually solve

REST: The Old Reliable

Pros:

  • Simple to understand (everyone knows it)
  • Cacheable by default (HTTP caching works)
  • Mature tooling (Postman, curl, Swagger)
  • Stateless and scalable

Cons:

  • Over-fetching (get 50 fields, need 3)
  • Under-fetching (need user AND posts = 2 requests)
  • Endpoint explosion (v1, v2, etc.)

Use when: ✅ Public APIs, simple CRUD, team unfamiliar with GraphQL, need heavy caching, microservices

GraphQL: The Flexible Query Language

Pros:

  • No over-fetching (ask exactly what you need)
  • No under-fetching (related data in one query)
  • Strongly typed schema (auto-generate types)
  • No versioning (add fields backward-compatibly)

Cons:

  • Complex (200+ lines vs 50 for REST)
  • Caching is harder (everything POSTs to /graphql)
  • N+1 query problem (fetches author for each post)
  • Learning curve (team needs GraphQL knowledge)
  • Security concerns (expensive nested queries)

Use when: ✅ Complex nested data, multiple clients (web/mobile), rapid frontend iteration, team has GraphQL experience

❌ Simple CRUD, public API, small inexperienced team

tRPC: TypeScript Native

What it is: End-to-end TypeScript. No schema definition. Call backend functions from frontend like RPC.

Pros:

  • Full type safety (change backend → frontend knows immediately)
  • Great DX (autocomplete everywhere)
  • Small bundle (no heavy GraphQL client)
  • Simple for TypeScript teams

Cons:

  • TypeScript only (can’t use with Python, Go, Java)
  • Not for public APIs
  • Tight coupling (monorepo required)

Use when: ✅ Full-stack TypeScript, internal tools, monorepo, team loves types

❌ Public API, multi-language, mobile apps

Decision Matrix

  REST GraphQL tRPC
Learning curve Low High Medium
Type safety Manual Yes Native
Caching Easy Hard Medium
Public API
Mobile apps ⚠️
Complex data
Simple CRUD

My Recommendations

Startup MVP: REST (fastest to build)

Mobile + Web: GraphQL (different data needs)

Next.js full-stack: tRPC (best DX)

Public developer API: REST (most accessible)

Internal dashboard: tRPC (speed + types)

The Bottom Line

Stop choosing based on hype.

Choose based on:

  1. Team skills - Can they use it?
  2. Use case - Does it solve real problems?
  3. Constraints - Time, budget, existing systems?

REST isn’t dead. GraphQL isn’t always better. tRPC isn’t magic.

Most projects are fine with REST. If you have specific problems REST doesn’t solve, then consider GraphQL or tRPC.

But don’t adopt something just because it’s trendy.

Build boring stuff that works. Ship fast. Solve real problems.

The API paradigm matters way less than you think.