WebSocket Handshake Succeeds but No Messages Received (Rust + Axum Service)

lcnewhook
PROOP

18 days ago

Hi Railway Support,

I’m running into an issue with a WebSocket service I’ve deployed on Railway. The initial handshake completes successfully, but no messages are coming through from the server to the client after the connection is established.

Service Info

  • Service Name:rust-matching-engine

  • URL:https://laureate-matching-engine.railway.app

  • WebSocket Endpoint:wss://laureate-matching-engine.railway.app/ws

  • Stack: Rust + Axum 0.7 + Tokio

  • Docker: Multi-stage build, based on Debian bookworm-slim

What I’m Seeing

Locally (everything works):bash # ws://localhost:3002/ws Connects Receives: {"type":"auth_required"} Receives: {"type":"pong"} Receives: {"type":"auth_failed",...}

On Railway (connection succeeds, but...):bash # wss://...railway.app/ws Connects TLS handshake succeeds No messages received at all No errors or warnings

Things I’ve Already Checked

  • /health endpoint returns 200 — service is up

  • WebSocket upgrade works — handshake completes

  • Identical binary works fine locally

  • Using Axum’s standard WebSocketUpgrade implementation

  • send() calls succeed — logs confirm messages are being sent

  • Explicit .flush() calls added — no effect

  • Listening on 0.0.0.0:${PORT} — port binding is correct

Quick Test You Can Run

npm install ws jsonwebtoken

cat > test.js << 'EOF'
const WebSocket = require('ws');
const ws = new WebSocket('wss://laureate-matching-engine.railway.app/ws');

ws.on('open', () => {
  console.log('✅ Connected');
  ws.send(JSON.stringify({ type: 'ping' }));
});

ws.on('message', (data) => {
  console.log('📥 Received:', data.toString());
});

setTimeout(() => {
  console.log('❌ No messages received in 5 seconds');
  process.exit(1);
}, 5000);
EOF

node test.js

Expected:{"type":"auth_required"} should come back right after connect
Actual: Nothing is received

Core WebSocket Handler (Axum)

pub async fn websocket_handler(
    State(ws_server): State>,
    ws: WebSocketUpgrade,
    headers: HeaderMap,
) -> impl IntoResponse {
    info!("[WebSocket] Upgrade request received");
    ws.on_upgrade(move |socket| ws_server.handle_socket(socket))
}

self.send_message(&connection, WebSocketMessage::AuthRequired).await?;
conn.sender.send(Message::Text(json)).await?;
conn.sender.flush().await?;

A Few Questions

  1. Does Railway require any special config for WebSocket services?

  2. Is there any proxy buffering or header-related behavior that might block or delay messages?

  3. Are there known limitations or quirks with Axum + WebSockets on Railway?

  4. Can someone check the proxy logs on your end to see if messages are getting stuck?

Repo

Code is available here: https://github.com/lcnewhook/laureate

Relevant files: - backend/rust-engine/src/websocket.rs - backend/rust-engine/src/main.rs - backend/rust-engine/test-websocket-simple.js

This setup works flawlessly on my machine, but something seems to be going wrong when running behind Railway’s infra. Any help or pointers would be hugely appreciated!

Thanks again,
Lawrence Newhook

$10 Bounty

2 Replies

Railway
BOT

18 days ago

Hey there! We've found the following might help you get unblocked faster:

If you find the answer from one of these, please let us know by solving the thread!


monuit
PROTop 5% Contributor

17 days ago

hey, railway supports websockets over HTTP/1.1 as stated in their docs so you might have to configure hyper/axum to use http1_only(true)

for axum, im not too familiar with it, but looking at rust's docs, you might have to split and continuously read the socket with a receive loop.

let me know if that worked out! if it didnt, can you drop the logs for the redeployment?


WebSocket Handshake Succeeds but No Messages Received (Rust + Axum Service) - Railway Help Station