Ahmed Rehman
Ahmed Rehman

Reputation: 59

WebSocket Client in Flutter not Receiving Messages from Server (Netty WebSocket Server)

I am having trouble with WebSocket communication in my Flutter application. The server (using Netty) is successfully receiving the userId and responding with a message, but the Flutter WebSocket client is unable to receive any messages from the server. What I’ve Done So Far: Server Side (Netty WebSocket Server) Code: The server is built using Netty, and the WebSocket server is set up as follows:

public class WebSocketServer {

private final int port;

public WebSocketServer(int port) {
    this.port = port;
}

public void start() throws InterruptedException {
    EventLoopGroup bossGroup = new NioEventLoopGroup();
    EventLoopGroup workerGroup = new NioEventLoopGroup();

    try {
        ServerBootstrap serverBootstrap = new ServerBootstrap();
        serverBootstrap.group(bossGroup, workerGroup)
                .channel(NioServerSocketChannel.class)
                .childHandler(new ChannelInitializer<SocketChannel>() {
                    @Override
                    protected void initChannel(SocketChannel socketChannel) {
                        ChannelPipeline pipeline = socketChannel.pipeline();
                        pipeline.addLast(new HttpServerCodec());
                        pipeline.addLast(new HttpObjectAggregator(65536));
                        pipeline.addLast(new ChunkedWriteHandler());
                        pipeline.addLast(new WebSocketServerProtocolHandler("/ws"));
                        pipeline.addLast(new WebSocketFrameHandler());
                    }
                })
                .option(ChannelOption.SO_BACKLOG, 128)
                .childOption(ChannelOption.SO_KEEPALIVE, true);

        Channel channel = serverBootstrap.bind(port).sync().channel();
        System.out.println("WebSocket Server started on port " + port);
        channel.closeFuture().sync();
    } finally {
        bossGroup.shutdownGracefully();
        workerGroup.shutdownGracefully();
    }
}

// WebSocketFrameHandler handles the incoming WebSocket frames.
public class WebSocketFrameHandler extends SimpleChannelInboundHandler<TextWebSocketFrame> {
    @Override
    protected void channelRead0(ChannelHandlerContext ctx, TextWebSocketFrame msg) {
        // Print client info
        System.out.println("New client connected with userId: 1234 and assigned connectionId: " + ctx.channel().id().asLongText());

        // Send a message to the client
        ctx.channel().writeAndFlush(new TextWebSocketFrame("Welcome user 1234! Your connection ID is: " + ctx.channel().id().asLongText()));
    }
}

public static void main(String[] args) throws InterruptedException {
    new WebSocketServer(8080).start();
}

}

The server is running on ws://localhost:8080/ws and sends the response "Welcome user 1234! Your connection ID is: " to the client.

Flutter Client Code: In Flutter, I am using WebSocketChannel to connect to the WebSocket server and listen for messages:

import 'package:web_socket_channel/web_socket_channel.dart';

class SocketWithNetty extends StatefulWidget {
  const SocketWithNetty({super.key});

  @override
  State<SocketWithNetty> createState() => _SocketIoNewState();
}

class _SocketIoNewState extends State<SocketWithNetty> {
  late WebSocketChannel _channel;
  late TextEditingController _controller;
  String _message = '';

  @override
  void initState() {
    super.initState();

    // Initialize WebSocket connection
    _channel = WebSocketChannel.connect(Uri.parse('ws://localhost:8080/ws?userId=1234'));

    // Listen to WebSocket stream to receive messages
    _channel.stream.listen(
      (message) {
        setState(() {
          _message = message;
        });
      },
      onError: (error) {
        print("Error: $error");
      },
      onDone: () {
        print("WebSocket connection closed");
      },
    );

    _controller = TextEditingController();
  }

  @override
  void dispose() {
    _channel.sink.close();
    _controller.dispose();
    super.dispose();
  }

  void _sendMessage() {
    if (_controller.text.isNotEmpty) {
      _channel.sink.add(_controller.text);
    }
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: Text('WebSocket Client')),
      body: Padding(
        padding: const EdgeInsets.all(16.0),
        child: Column(
          crossAxisAlignment: CrossAxisAlignment.stretch,
          children: [
            TextField(
              controller: _controller,
              decoration: InputDecoration(labelText: 'Send a message'),
            ),
            SizedBox(height: 16),
            ElevatedButton(
              onPressed: _sendMessage,
              child: Text('Send Message'),
            ),
            SizedBox(height: 16),
            Text('Server Response: $_message'),
          ],
        ),
      ),
    );
  }
}

Problem:

Upvotes: 0

Views: 41

Answers (0)

Related Questions