Create client with custom validateMessage and parseMessage
See original GitHub issueStory
Hi, thank you for doing all work by creating and managing this repo its great! Maybe my usecase will be not wide used but anyway.
I have a client that has a proxy server and then regular server. When i establish a ws connection, by proxy server i create a websocket stream by createWebSocketStream()
from ws
package and basically communicating with binary data.
As i can see graphql-ws
has a restriction thats in validateMessage
checks if message that comes from ws is a JSON or UTF8 as you wish.
I just want to be able to obtain this information that this is a buffer or another type and translate it to a UTF8 or JSON so graphql-ws
wont fail on this validation error.
It happens at the beginning when I send { type: "connection_init" }
my server gets it, and returns { type: "connection_ack"}
but proxy server makes it a binary stream and on client i get Binary Message
instead of JSON. If i copy this resposne as UTF8 i can see that this is a correct { type: "connection_ack"}
but it comes as a Blob
and fails on Message is missing the 'type' property
inside validateMessage
from graphql-ws
because its not JSON and doesnt have a type property.
I must use proxy with binary data for another technical reason that isnt valuable, so its not an option to just simply swith to JSON messages for ws.
Simply trying converting message from ws before sending it to a validateMessage or parseMessage function is enough. Or can it be exposed to a createClient()
options function so it will be configurable for other people too ?
Something like
export { createClient } from "graphql-ws"
const client = createClient({
url: "ws://localhost:3001/graphql,
parseMessage: async (message) => if (message instanceof Blob) return await message.text()
})
Its just need to be called before a validateMessage().
Or in a current validateMessage just check for Blob and parse it before do actual validation.
const message = message instanceof Blob ? await data.text() : data
return validateMessage(
typeof data === 'string' ? JSON.parse(data, reviver) : data,
);
Regardless of mine reasons not to use a JSON over websockets messages people use binary streams as its less data and less weight, can be transported bigger chunks and means more users and so on.
Thank you!
Issue Analytics
- State:
- Created a year ago
- Comments:5 (3 by maintainers)
Yeah, i agree that the format should remain JSON, it makes sense. I will create a PR for elevating requirements for stringify method. It makes sense for me to support both data representation that WebSocket API is providing, so it means this elevations of stringify mehtod shouldnt be hundrends, bc we can have either JSON or Binary and it wouldnt polute codebase with more and more elevations.
Cool, looking forward to the PR.
Closing this issue in favor of the solution at: https://github.com/enisdenjo/graphql-ws/issues/409#issuecomment-1271315726.