Authentication in Websockets
In the server side, how do you make sure the client is authenticated, given that Authorisation headers are not allowed in the ws protocol (not even in the first http handshake).
Analogue to that, in the client side, how do you authenticate with JWT Tokens ? Do you send the token on every web socket message ?
5 Replies
Unknown User•2y ago
Message Not Public
Sign In & Join Server To View
I've never done what you're asking, but isn't it easier to use cookies to manage auth? Maybe that fix your not headers thing.
Following this thread for updates as I don't have a definitive answer for this, but I was able to successfully implement WS auth with JWTs in a TypeScript chat app I built a few months ago: https://github.com/ChromeUniverse/LuccaChat
GitHub
GitHub - ChromeUniverse/LuccaChat: A full-stack live chat app, powe...
A full-stack live chat app, powered by TypeScript, React, Express and ws - GitHub - ChromeUniverse/LuccaChat: A full-stack live chat app, powered by TypeScript, React, Express and ws
Here's the gist of my approach: keep a
Map()
or some other sort of memory store of user IDs and websocket connections, this will allow you to look up who sent the incoming message in your DB and perform whatever business logic you need. Unfortunately this won't scale past a single instance of the WS server though, unless you use something like Redis I'd imagine...
https://github.com/ChromeUniverse/LuccaChat/blob/main/server/src/wss.ts
Here is the actual WS authentication handler itself:
https://github.com/ChromeUniverse/LuccaChat/blob/main/server/src/websockets-handlers/auth.ts
I've cropped the snippets above for brevity but I've linked the full files on GitHub as well
Here's the basic flow:
- User sends an auth request message to the WS server
- Auth request message contains a JWT that was originally signed by my REST API
- WS server verifies the authenticity of the JWT
- If auth succeeds, the user will get pushed to the userSocketMap
which binds their WS connection to their user ID for handling later WS message exchange
- If auth fails, the WS server just severs the connection
Hope this helps, but I'm sure there's a better way to implement this...Thank you for your answer 🙂 The ticket message is indeed the best alternative - I should've elaborate my question a bit more since this is in the context of only one tRPC server that runs both the http and the ws connections. The ticket System is only possible with the ws and the http server being separated. But you're right!
Thank you, same as what I told to @LeoRoese this is in the context of only one tRPC server that runs both the http and the ws connections.... this means that I would like to do this in the createContext function of the tRPC handlers. But technically your answer is correct to how I express my question. Thats an efficient way of doing auth with WS and JWT tokens 🙂 thanks!
I think I will ask a new question with more context, since this one was a bit incomplete, and your answers are already answering what I asked 🙂 thanks!