Skip to content

Commit f79bf78

Browse files
authored
feat: improve ws protocol and closure handling (#123)
* feat: improve ws protocol and closure handling Fixes #63 and fixes #64. * require recent enough crossws * fix linter * reuse graphql closecode
1 parent 7a83402 commit f79bf78

File tree

3 files changed

+18
-14
lines changed

3 files changed

+18
-14
lines changed

examples/websocket.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ const resolvers = {
3333
},
3434
Subscription: {
3535
numberIncremented: {
36-
subscribe: () => pubsub.asyncIterator(['NUMBER_INCREMENTED']),
36+
subscribe: () => pubsub.asyncIterableIterator(['NUMBER_INCREMENTED']),
3737
},
3838
},
3939
}

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@
3838
"h3": "^1.11.0",
3939
"graphql": "^16.0.0",
4040
"graphql-ws": "^5.0.0 || ^6.0.0",
41-
"crossws": "^0.2.4 || ^0.3.0"
41+
"crossws": "^0.3.0"
4242
},
4343
"peerDependenciesMeta": {
4444
"graphql-ws": {

src/websocket.ts

Lines changed: 16 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -43,9 +43,8 @@ export async function defineGraphqlWebSocket<
4343
E extends Record<PropertyKey, unknown> = Record<PropertyKey, never>,
4444
>(options: ServerOptions<P, Extra & Partial<E>>): Promise<Partial<Hooks>> {
4545
// Local import since graphql-ws is only an optional peer dependency
46-
const { makeServer, GRAPHQL_TRANSPORT_WS_PROTOCOL } = await import(
47-
'graphql-ws'
48-
)
46+
const { makeServer, DEPRECATED_GRAPHQL_WS_PROTOCOL, CloseCode } =
47+
await import('graphql-ws')
4948
const server = makeServer(options)
5049
const peers = new WeakMap<Peer, Client>()
5150
return defineWebSocket({
@@ -61,20 +60,16 @@ export async function defineGraphqlWebSocket<
6160

6261
client.closed = server.opened(
6362
{
64-
// TODO: use protocol on socket once h3 exposes it
65-
// https://github.com/unjs/crossws/issues/31
66-
protocol: GRAPHQL_TRANSPORT_WS_PROTOCOL,
63+
protocol: peer.request.headers?.get('Sec-WebSocket-Protocol') ?? '',
6764
send: (message) => {
6865
// The peer might have been destroyed in the meantime, send only if exists
6966
if (peers.has(peer)) {
7067
peer.send(message)
7168
}
7269
},
73-
close: (_code, _reason) => {
70+
close: (code, reason) => {
7471
if (peers.has(peer)) {
75-
// TODO: No way to close a connection in crossws
76-
// https://github.com/unjs/crossws/issues/23
77-
// peer.close(code, reason);
72+
peer.close(code, reason)
7873
}
7974
},
8075
onMessage: (cb) => (client.handleMessage = cb),
@@ -91,8 +86,17 @@ export async function defineGraphqlWebSocket<
9186
close(peer, details) {
9287
const client = peers.get(peer)
9388
if (!client) throw new Error('Closing a missing client')
94-
// TODO: Once h3 exposes the protocol, add a check here for deprecated protocols
95-
// similar to https://github.com/enisdenjo/graphql-ws/blob/6013eb54829b27bd7c598f0985ec80a0e1acf09c/src/use/deno.ts#L109-L116
89+
const upgradeProtocol = peer.request.headers?.get(
90+
'Sec-WebSocket-Protocol',
91+
)
92+
if (
93+
details.code === CloseCode.SubprotocolNotAcceptable &&
94+
upgradeProtocol === DEPRECATED_GRAPHQL_WS_PROTOCOL
95+
)
96+
console.warn(
97+
`Client provided the unsupported and deprecated subprotocol "${upgradeProtocol}" used by subscriptions-transport-ws.` +
98+
'Please see https://www.apollographql.com/docs/apollo-server/data/subscriptions/#switching-from-subscriptions-transport-ws.',
99+
)
96100
return client.closed(details.code, details.reason)
97101
},
98102
})

0 commit comments

Comments
 (0)