Java客户端到服务器未知来源

时间:2013-02-16 19:08:18

标签: java sockets networking tcp

我有一个简单的乒乓球游戏,需要通过网络工作,服务器将创建一个具有球和2个球的位置的游戏,当客户端连接到服务器时,服务器将创建一个名为PongPlayerThread的新类它将处理客户端到服务器的输入和输出流,

我的服务器工作100%没有任何数据从客户端到服务器,服务器可以发送信息给客户端没有任何问题,但我有一个奇怪的问题,但首先这里是我的代码,所以你可以看到什么我有。

PongServer

try
{
    serverSocket = new ServerSocket(port);
    listen = true;
    System.out.println("Server was setup and will try to create a socket");
}
catch(IOException e)
{
    System.err.println("Could not listen on port:" + port);
    System.exit(1);
}

while(listen)
{
    players[idPlayer] = new PongPlayerThread(serverSocket.accept(), idPlayer, rtnInfo());
    players[idPlayer].start();
    System.out.println("Client Connected with ID:" + idPlayer);
    players[0].passData(rtnInfo());
    idPlayer++;     
    if(idPlayer > 1)
    {
        listen = false;
        playing = true;
    }
}

while(playing)
{
    players[0].passData(rtnInfo());
    players[0].sleep(25);
    players[1].passData(rtnInfo());
    players[1].sleep(25);
}

....//more, but not important

这是我的PongClient

try
{
    socket = new Socket(host, port);
    serverOut = new PrintWriter(socket.getOutputStream(), true);
    serverInput = new BufferedReader(new InputStreamReader(socket.getInputStream()));
}
catch (UnknownHostException e)
{
    System.err.println("Couold not connect to host:" + host);
    System.exit(1);
}
catch (IOException e)
{
    System.err.println("Could not get Input/Output from server");
    System.exit(1);
}

...

while ((pos = serverInput.readLine()) != null) 
{
    String text = "nothing";
    serverOut.println(text);
    String[] posValues = pos.split(":");
        model.getBall().setX(Double.parseDouble(posValues[0]));
        model.getBall().setY(Double.parseDouble(posValues[1]));


    /*if(PongController.moveUp == true)
    {
        System.out.println("Up");
        serverOut.println("up");
        PongController.moveUp = false;
    }
    else
    {
        serverOut.println("nothing");
    }*/

}

这是我的PongPlayerThread

try
{
    PrintWriter out = new PrintWriter(socket.getOutputStream(), true);
    BufferedReader in = new BufferedReader(
        new InputStreamReader(
        socket.getInputStream()));

    String text = "hhh";

    System.out.println(in.toString());
    //System.out.println(text = in.readLine());
    System.out.println("Checking readLine value");

    String line; 
    if ((line = in.readLine()) == null) 
    { 
        System.out.println("A ok"); 
    } 
    else 
    { 
        System.out.println(":" + line); 
    }

    while(send)
    {
        //String temp = in.readLine();
        //if(temp.equals("up"))
        //{
        //        System.out.println("Up you say");
        //}
        out.println(pongData);
    }

    out.close();
    in.close();
    socket.close();
}

catch (IOException e) 
{
    e.printStackTrace();
}

现在当我运行我的服务器时它很好,然后连接客户端,当客户端连接乒乓球时它应该静止等待另一个玩家,但是球只会更新自己而不从服务器获取数据,一旦我关闭客户端程序,我的服务器就会出现此错误

java.net.SocketException: Connection reset
at java.net.SocketInputStream.read(Unknown Source)
at sun.nio.cs.StreamDecoder.readBytes(Unknown Source)
at sun.nio.cs.StreamDecoder.implRead(Unknown Source)
at sun.nio.cs.StreamDecoder.read(Unknown Source)
at java.io.InputStreamReader.read(Unknown Source)
at java.io.BufferedReader.fill(Unknown Source)
at java.io.BufferedReader.readLine(Unknown Source)
at java.io.BufferedReader.readLine(Unknown Source)
at Pong.PongPlayerThread.run(PongPlayerThread.java:42)

PongPlayerThread中的第42行是

if ((line = in.readLine()) == null) 

我一直试图解决这个问题好几天,但我还是没有找到解决方案,我觉得inputStream无法连接到客户端的outputStream,我试过使用wireShark但是这是一个局域网程序,所以它不起作用,并且没有任何东西会出现在wireShark中。如果有人能够对此发光,那将非常感激。

帆布

iTech更新 好的,我在这里使用你的代码就是我现在的PongPlayerThread

public void run()
{
    try
    {
        PrintWriter out = new PrintWriter(socket.getOutputStream(), true);
        BufferedReader in = new BufferedReader(
                    new InputStreamReader(
                    socket.getInputStream()));

        String text = "hhh";

        System.out.println(in.toString());
        //System.out.println(text = in.readLine());
         System.out.println("Checking readLine value");

         String line = null; 
         if ((line = in.readLine()) != null) // why you check if it is null !?
         { 
             System.out.println("Client sent: "+line); 
         } 

        while(send)
        {
            out.println(pongData);
        }

         out.close();
         in.close();
         socket.close();
    }

这会在控制台“Client sent:Hello”中说,但我的客户端不会停止并继续从服务器获取数据,

如果我把if语句放到while语句中,它有out.println(pongData)它可以工作,但是一旦客户端连接和断开连接我就会收到错误,或者如果两个客户端连接然后它们会出错两个人都离开我再次得到这个错误:(

java.net.SocketException: Connection reset
at java.net.SocketInputStream.read(Unknown Source)
at sun.nio.cs.StreamDecoder.readBytes(Unknown Source)
at sun.nio.cs.StreamDecoder.implRead(Unknown Source)
at sun.nio.cs.StreamDecoder.read(Unknown Source)
at java.io.InputStreamReader.read(Unknown Source)
at java.io.BufferedReader.fill(Unknown Source)
at java.io.BufferedReader.readLine(Unknown Source)
at java.io.BufferedReader.readLine(Unknown Source)
at Pong.PongPlayerThread.run(PongPlayerThread.java:45)

和第45行是

if ((line = in.readLine()) != null) // why you check if it is null !?

将代码排序,但现在在我的pongClient代码中

 while ((pos = serverInput.readLine()) != null) 
    {
        String text = "nothing";
        serverOut.println(text);
        String[] posValues = pos.split(":");
        model.getBall().setX(Double.parseDouble(posValues[0]));
        model.getBall().setY(Double.parseDouble(posValues[1]));


        if(PongController.moveUp == true)
        {
            System.out.println("Up");
            serverOut.println("up");
            PongController.moveUp = false;
        }
        else
        {
            serverOut.println("nothing");
        }

    }

一旦碰到它,它就不会做任何事情,并且会再次导致整个错误。

我发现错误,我放了

 if ((line = in.readLine()) != null)
             { 

如果再次放入line = in.readLine(),则会导致错误。奇怪,但它现在已修复,数据可以从客户端发送到服务器,服务器发送到客户端:)

2 个答案:

答案 0 :(得分:0)

一旦客户端连接到您的服务器,if ((line = in.readLine()) == null)将阻止该线程,直到从客户端收到消息。

您需要在建立连接后从客户端发送内容

PongPlayerThread中,您可以修改以下内容并删除else

String line = null; 
if ((line = in.readLine()) != null) // why you check if it is null !?
{ 
    System.out.println("Client sent: "+line); 
} 

在建立PongClient连接后的socket中,您可以发送一些消息,例如serverOut.println("Hello");

答案 1 :(得分:0)

'连接重置'有几个原因,但最常见的原因是您已写入已被另一端关闭的连接。换句话说,应用程序协议错误。