Skip to content

chore: add support for one-way websockets to backend #16853

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 11 commits into from
Mar 28, 2025
Merged

Conversation

Parkreiner
Copy link
Member

@Parkreiner Parkreiner commented Mar 7, 2025

Closes #16775
Part 1/2, with #16855 handling the frontend changes

Changes made

  • Added OneWayWebSocket function that establishes WebSocket connections that don't allow client-to-server communication
  • Added tests for the new function
  • Updated API endpoints to make new WS-based endpoints, and mark previous SSE-based endpoints as deprecated
  • Updated existing SSE handlers to use the same core logic as the new WS handlers

@Parkreiner
Copy link
Member Author

@Emyrk Just pinging you in case you didn't see this. Let me know if you're busy, and I can find someone else to review this

@Parkreiner Parkreiner requested review from f0ssel and removed request for Emyrk March 18, 2025 13:46
@Parkreiner
Copy link
Member Author

@f0ssel Steven is really heads-down on Mango stuff right now. Would you be able to take over review for this?

Copy link
Contributor

@f0ssel f0ssel left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Overall this looks great, the tests are really good coverage and the shared implementation worked out nice.

I suggested some naming changes, mainly because we don't use "callback" very much in Go and like to use "-er" words to describe capabilities.

@@ -282,7 +285,25 @@ func WebsocketCloseSprintf(format string, vars ...any) string {
return msg
}

func ServerSentEventSender(rw http.ResponseWriter, r *http.Request) (sendEvent func(ctx context.Context, sse codersdk.ServerSentEvent) error, closed chan struct{}, err error) {
type InitializeConnectionCallback func(rw http.ResponseWriter, r *http.Request) (
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
type InitializeConnectionCallback func(rw http.ResponseWriter, r *http.Request) (
type EventSender func(rw http.ResponseWriter, r *http.Request) (

// open a workspace in multiple tabs, the entire UI can start to lock up.
// WebSockets have no such limitation, no matter what HTTP protocol was used to
// establish the connection.
func OneWayWebSocket(rw http.ResponseWriter, r *http.Request) (
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
func OneWayWebSocket(rw http.ResponseWriter, r *http.Request) (
func WebSocketEventSender(rw http.ResponseWriter, r *http.Request) (

Comment on lines 439 to 442
type SocketError struct {
Code websocket.StatusCode
Reason string
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be declared at the package level.

And just to double check, there isn't already a type like this in websocket is there?

Comment on lines 164 to 171
// Our WebSocket library accepts any arbitrary ResponseWriter at the type level,
// but it must also implement http.Hijack
type mockWsResponseWriter struct {
serverRecorder *httptest.ResponseRecorder
serverConn net.Conn
clientConn net.Conn
serverReadWriter *bufio.ReadWriter
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

return w(b)
}

func TestOneWayWebSocket(t *testing.T) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because we also touch the SSE Sender, could we include some basic coverage for that if there isn't already?

@Parkreiner Parkreiner requested a review from f0ssel March 20, 2025 15:19
@Parkreiner
Copy link
Member Author

@f0ssel Forgot to ping you yesterday, but I applied all your feedback and added tests for the SSE code

Closes #16777

## Changes made
- Added `OneWayWebSocket` utility class to help enforce one-way
communication from the server to the client
- Updated all client client code to use the new WebSocket-based
endpoints made to replace the current SSE-based endpoints
- Updated WebSocket event handlers to be aware of new protocols
- Refactored existing `useEffect` calls and removed some synchronization
bugs
- Removed dependencies and types for dealing with SSEs
- Addressed some minor Biome warnings
@Parkreiner Parkreiner merged commit 9bc727e into main Mar 28, 2025
35 checks passed
@Parkreiner Parkreiner deleted the mes/one-way-ws-01 branch March 28, 2025 21:13
@github-actions github-actions bot locked and limited conversation to collaborators Mar 28, 2025
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Add support for One-Way WebSocket communication to backend
2 participants