SyntaxStudy
Sign Up
GraphQL GraphQL Subscriptions and WebSockets
GraphQL Beginner 1 min read

GraphQL Subscriptions and WebSockets

Subscriptions are GraphQL's mechanism for real-time data. The client sends a subscription operation over a persistent connection (typically WebSocket) and the server pushes updates whenever a relevant event occurs. The graphql-ws library implements the modern GraphQL over WebSocket Protocol (v5.14+). Apollo Server integrates subscriptions via a separate WebSocket server running alongside the HTTP server. The subscription resolver uses an asyncIterator from a PubSub instance to yield events to all subscribed clients.
Example
// npm install graphql-ws ws @graphql-tools/schema

import { createServer } from 'http';
import { WebSocketServer } from 'ws';
import { useServer } from 'graphql-ws/lib/use/ws';
import { PubSub } from 'graphql-subscriptions';
import { makeExecutableSchema } from '@graphql-tools/schema';

const pubsub = new PubSub();
const MESSAGE_SENT = 'MESSAGE_SENT';

const typeDefs = `#graphql
  type Message { id: ID!  text: String!  sender: String!  sentAt: String! }
  type Query    { messages: [Message!]! }
  type Mutation { sendMessage(text: String!, sender: String!): Message! }
  type Subscription { messageSent: Message! }
`;

const resolvers = {
  Mutation: {
    sendMessage: (_, args) => {
      const message = { id: Date.now().toString(), ...args, sentAt: new Date().toISOString() };
      pubsub.publish(MESSAGE_SENT, { messageSent: message });
      return message;
    },
  },
  Subscription: {
    messageSent: {
      subscribe: () => pubsub.asyncIterator([MESSAGE_SENT]),
    },
  },
};

const schema = makeExecutableSchema({ typeDefs, resolvers });
const httpServer = createServer();
const wsServer = new WebSocketServer({ server: httpServer, path: '/graphql' });
useServer({ schema }, wsServer);
httpServer.listen(4000, () => console.log('WS ready at ws://localhost:4000/graphql'));