Course
GraphQL
69 lessons across 8 modules
Intermediate to advanced, assuming JavaScript or TypeScript, REST basics and some Node.js. Fundamentals and the comparison with REST, schema and types, queries and mutations, resolvers, a real server, the React client, then the advanced and production concerns GraphQL creates that REST does not. The road is laid out in full; lessons are being written one at a time.
GraphQL Fundamentals
What it is, and what it costs you
Building REST APIs, for the comparison →What is GraphQL?
1A query language and a type system - not a database, not a framework.
One request returning exactly the fields asked for
Why GraphQL?
2Over-fetching, under-fetching, and the round trips REST forces.
Three REST calls collapsing into one query
GraphQL vs REST
3An honest comparison, including where REST is still the better answer.
Caching, status codes, and what you give up
GraphQL Architecture
4Schema, resolvers, and the single endpoint everything goes through.
Drawing the pieces before writing any of them
Request and Response Flow
5Parse, validate, execute, respond - and where each can fail.
Following one query through all four stages
GraphQL Operations
6Query, mutation, and subscription - the three things you can send.
The same data read, changed, and watched
When to Use GraphQL
7The conditions that justify it, and the ones that do not.
A single client and one team, better served by REST
Schema and Types
The contract everything else is checked against
Schema
8SDL, the root types, and the schema as the actual API.
A schema file read as documentation
Object Types
9Types and their fields - the nouns of your domain.
Modelling a Course and its Lessons
Scalar Types
10The five built-ins, and writing a custom scalar.
A DateTime scalar that validates on the way in
Lists
11List types, and the four ways nullability combines with them.
[Course], [Course!], [Course]! and [Course!]! compared
Non-Null Types
12The exclamation mark, and why it is harder to remove than to add.
A non-null field that makes one error blank a whole list
Enums
13A closed set of values, checked before a resolver runs.
A status field that cannot be misspelled
Interfaces
14Shared fields across types, and querying them.
A Node interface with an id on everything
Unions
15One field returning several unrelated types.
A search result that is a Course or a Lesson or a User
Input Types
16Why arguments need their own types, and how to shape them.
One input object instead of nine arguments
Queries and Mutations
Writing the operations a client sends
Queries
17Asking for a shape, and getting that shape back.
The response mirroring the request, field for field
Fields
18Selection sets, nesting, and the depth you are allowed.
Walking from a course to its lessons to their authors
Arguments
19Filtering and parameterising at any level, not just the root.
Arguments on a nested field, not only the top one
Aliases
20Requesting the same field twice under different names.
Two courses fetched in one query
Fragments
21Reusing a selection set, and colocating it with a component.
A fragment per component, composed at the page
Variables
22Parameterising an operation instead of building strings.
Why string interpolation into a query is a bug
Mutations
23Writes, their return values, and why they resolve in series.
A mutation returning the record it just changed
Multiple Operations
24Several operations in one document, and naming them.
Choosing which operation to run by name
Resolvers
The functions that actually produce the data
What is a Resolver?
25One function per field, and the default you usually get free.
The resolver you did not write, and what it does
Resolver Structure
26The map from types to fields to functions.
A resolver map beside the schema it implements
Parent
27The first argument - what the level above returned.
A lesson resolver reading its course id from parent
Arguments
28The second argument, already validated against the schema.
Trusting args for shape, never for authorization
Context
29Per-request state - the user, the database, the loaders.
Building context once per request, not per field
ResolveInfo
30The fourth argument, and the one advanced use it has.
Reading the selection set to avoid over-fetching
Nested Resolvers
31How a tree of fields resolves, and in what order.
A query three levels deep, traced
Resolver Composition
32Wrapping resolvers for auth, logging, and validation.
One authenticated() wrapper used across a schema
Error Handling
33Throwing from a resolver, and what the client receives.
Partial data alongside an errors array
Setting Up a GraphQL Server
34The pieces you need, and the smallest server that runs.
Hello world over a single endpoint
Apollo Server
35Setup, plugins, and the context function.
A server with auth context and a logger plugin
Schema Definition
36Organising SDL across files as the schema grows.
A schema split by domain rather than by type kind
Resolvers
37Wiring resolvers to the schema, and keeping them thin.
A resolver that calls a service and nothing else
PostgreSQL Integration
38Relational data behind a graph, and the joins it implies.
A nested query and the SQL it really runs
MongoDB Integration
39Document data behind a graph, and where it fits better.
The same schema served from documents
Service Layer
40Business logic outside resolvers, so it stays testable.
Swapping the database without touching a resolver
Building a Complete API
41Schema, resolvers, services, and a database, end to end.
A courses API with full CRUD
GraphQL with React
Consuming a graph from the client
The React course →Apollo Client
42Setup, the link chain, and where the cache sits.
A client with auth headers and an error link
Queries from React
43useQuery, and the hook result read properly.
A course list with no fetch written by hand
Mutations
44useMutation, and what to do once it resolves.
Creating a course and refreshing what should change
Variables
45Passing arguments from component state into an operation.
A search box driving a parameterised query
Loading and Error States
46First load, refetch, and partial data with errors.
A response that is both successful and failed
Caching
47The normalized cache, and why ids matter so much.
One record updating everywhere it appears
Cache Updates
48Refetching against writing to the cache directly.
An insert that updates a list without a round trip
Optimistic UI
49Rendering the expected result, and rolling it back.
A toggle that reverts when the server refuses
Advanced GraphQL
Auth, pagination, subscriptions, and N+1
Authentication
50Identifying the caller once, in context, per request.
A token verified before any resolver runs
Authorization
51Field-level and resolver-level checks - and never in the client.
A field one role may read and another may not
Pagination
52Offset against cursor, and the Relay connection shape.
edges, nodes, and pageInfo explained once
Filtering
53Filter inputs that stay expressive without becoming SQL.
A filter input that the database can actually use
Sorting
54Sort arguments, defaults, and stable ordering.
Pagination breaking without a tiebreaker
File Uploads
55Multipart uploads, and why signed URLs are usually better.
Uploading beside the graph rather than through it
Subscriptions
56Live data over WebSockets, and what it costs to run.
A notification pushed to one connected client
DataLoader
57Batching and per-request caching, and where to construct it.
A loader shared across one request and no longer
The N+1 Problem
58Why a graph invites it, and how to see it happening.
One query producing 101 database calls
Performance Optimization
59Measuring per-resolver cost before changing anything.
A trace showing which field is actually slow
Production GraphQL
The problems GraphQL creates that REST does not
Error Handling
60Error codes, partial success, and not leaking internals.
A stack trace that reached a client
Security
61Introspection, batching abuse, and the single-endpoint surface.
What an attacker learns from introspection alone
Query Complexity
62Depth and cost limits, because any client can ask for anything.
A deeply nested query that would never return
Rate Limiting
63Limiting by cost rather than by request count.
Why one endpoint breaks per-route rate limits
Caching
64Response, field, and persisted-query caching - and HTTP caching lost.
Getting a CDN back in front of a graph
Monitoring
65Per-field metrics, and which operations actually run.
Finding the resolver behind a latency spike
Logging
66Logging operations without recording variables you must not keep.
An operation log that redacts a password variable
Testing
67Schema, resolvers, and integration through real operations.
A test that runs a query against a test server
Versioning and Schema Evolution
68Additive change, deprecation, and never shipping v2.
Removing a field only after nobody queries it
Production Best Practices
69The decisions worth making before launch, not after.
A pre-launch review of a real schema