简体   繁体   中英

Java tcp socket does not receive properly

Hi let me get straight to the problem. I have a big JSON packet that the server sends to this client once the client is authenticated

But the packet comes back in a weird way like it's split or something example:

The JSON should be:

Received: {"UserID":1,"PlayerID":2,"EXP":0,"Lvl":1,"Coins":0,"ItemSlots":30}

When it comes through:

Received: {"UserID":1,"PlayerID":2,"EXP":0,"Lvl":1,"Coins":0,
Received: "ItemSlots":30}

Why does it split the packet or something when it comes to the client and how can I fix this anyway?

Java Receive Code:

   private class ClientThread extends Thread {
        public void run() {
            try {
                while (selector.select() > 0) {
                    for (SelectionKey sk : selector.selectedKeys()) {

                        selector.selectedKeys().remove(sk);
                        if (sk.isReadable()) {

                            SocketChannel sc = (SocketChannel)sk.channel();
                            ByteBuffer buff = ByteBuffer.allocate(1024);
                            String content = "";

                            while (sc.read(buff) > 0) {
                                sc.read(buff);
                                buff.flip();
                                content += charset.decode(buff);
                                buff.clear();
                            }

                            System.out.println("Recieved: " + content);
                            sk.interestOps(SelectionKey.OP_READ);
                        }
                    }
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

Thanks have a wonderful day.

TCP protocol does not maintain message boundaries. It is not guaranteed that what the server sends is received as-is by the client and vice-versa.

If the server sends 1000 bytes data, the client application can receive the same across multiple recv or single recv . TCP does not guarantee any behaviour. "Split" can happen, it is upto the application to handle the data coming in multiple chunks, coalesce it to one unit of application data for further processing. One can see this particularly with large data sizes.

It looks like you've got a non-blocking socket channel, meaning that the while (sc.read(buff) > 0) { loop is terminating due to sc.read(buff) returning 0 since only a portion of the data sent has, at this point, been received.

Why does it split the packet or something when it comes to the client

Most likely the data is being split into two or more packets.

and how i can i fix this anyway?

Keep filling your buffer until the socket is closed by the server ( read should return -1 rather than 0 in that case). You need to maintain a separate buffer per channel. If the server doesn't close its end after sending the data, you'll need to delineate in some other way; you could prefix the JSON blob with a size header, for instance.

Hi lemme get straight to the problem so i got a big JSON packet that the server sends to this client once the client is authenticated

You mean you have a big JSON message . Packets are things that network protocols used to exchange information.

But the packet comes back in a weird way like its split or something example:

Unless you're looking at the wire, you aren't looking at packets. You're looking at the bytes you got from your end of the TCP connection.

The JSON should be:

Recieved: {"UserID":1,"PlayerID":2,"EXP":0,"Lvl":1,"Coins":0,"ItemSlots":30}

When it comes through:

Recieved: {"UserID":1,"PlayerID":2,"EXP":0,"Lvl":1,"Coins":0, Recieved: "ItemSlots":30}

Excellent. You got the same bytes. Now make a JSON parser that figures out where the message ends and parses it.

Why does it split the packet or something when it comes to the client

It splits the message into packets because that's how TCP gets the message to the other side. TCP is not a message protocol and it doesn't know or care what the application considers to be a message -- that's the application's job.

and how i can i fix this anyway?

Write a JSON parser to figure out where the messages end. You haven't implemented any code to receive JSON over TCP yet, so that won't work until you do.

TL;DR: If you want an application-level message protocol, you need to implement one. TCP is not one.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM