Question

Should be a simple fix that i am not able to correct. I am returning a total calculation, price * quantity, between the server and the client. However, I am receiving a java.net.SocketException: Connection Reset. I have inserted a ComputerServer class w/class HandleAClient, ComputerClient class and Computer class. I welcome any help. Thank you!

import java.io.*;
import java.util.*;
import java.net.*;
import java.util.concurrent.Executors;
import java.util.concurrent.ExecutorService;

public class ComputerServer 
{
    public static void main(String args[])
    {
        ServerSocket serverSocket;
        Socket connection;

        ObjectInputStream input;
        ObjectOutputStream output;

        Computer c = null;

        Object obj;

        double totalCharge;

        try
        {
            serverSocket = new ServerSocket(8000);
            System.out.println("Waiting for Client");

            int clientNo = 1;

            ExecutorService threadExecutor = Executors.newCachedThreadPool();

            while(true)//runs indefinitely
            {
                connection = serverSocket.accept();

                input = new ObjectInputStream(connection.getInputStream());
                output = new ObjectOutputStream(connection.getOutputStream());

                obj = input.readObject();

                System.out.println("Object Received from client:\n"+obj);

                if(obj instanceof Computer)
                {
                    totalCharge = ((Computer)obj).getPrice()*((Computer)obj).getQuantity();

                    HandleAClient thread = new HandleAClient(connection, clientNo, totalCharge);

                    threadExecutor.execute(thread);

                    output.writeObject(totalCharge);
                    output.flush();
                }





                clientNo++;
            }

        }
        catch(ClassNotFoundException cnfe)
        {
            cnfe.printStackTrace();
        }
        catch(IOException ioe)
        {
            ioe.printStackTrace();
        }

    }//end of main
}

class HandleAClient implements Runnable
{
    //**SHOULD i do object...
    //Scanner input;
    //Formatter output;
    Object obj;

    ObjectOutputStream output;
    ObjectInputStream input;

    Socket connection;
    ServerSocket serverSocket;

    int clientNo;

    //variables for calculation
    //variables for calculation
    double price;
    double totalCharge;


    public HandleAClient(Socket connection, int clientNo, double totalCharge)
    {
        this.connection = connection;
        this.clientNo = clientNo;
        this.totalCharge = totalCharge;
    }

    public void run()
    {
        //ArrayList<Computer> cList = new ArrayList<Computer>();

        try
        {


            input = new ObjectInputStream(connection.getInputStream());
            output = new ObjectOutputStream(connection.getOutputStream());


            /*while(input.hasNext())
            {
                //variable = input.next....
                //print out calculation
                price = input.nextDouble();
                System.out.println("Price received from client:\t"+clientNo+"is"+price);

                //DO CALCULATION, STORE IT

                for(Computer c: cList)//**TRYING a for loop
                {
                    totalCharge = ((Computer)c).getPrice() * ((Computer)c).getQuantity();

                    output.format("%.2f\n", totalCharge);

                    //output.flush();
                }
            //}*/

            System.out.println("TotalCharge"+totalCharge);
            System.out.println("Thread"+"\t"+clientNo+"\t"+"ended");
        }
        catch(IOException ioe)
        {
            ioe.printStackTrace();
        }
    }
}

    import java.util.*;
import java.io.*;
import java.net.*;

public class ComputerClient 
{
    public static void main(String args[])
    {
        Socket connection;

        ObjectOutputStream output;
        ObjectInputStream input;

        Object obj;

        Computer c = new Computer("Asus",1189.99,4);

        try
        {
            connection = new Socket("localhost",8000);

            output = new ObjectOutputStream(connection.getOutputStream());
            input = new ObjectInputStream(connection.getInputStream());

            output.writeObject(c);
            output.flush();

            //read back:

            obj=(Object)input.readObject();

            System.out.println(obj.toString());
        }
        catch(ClassNotFoundException cnfe)
        {
            cnfe.printStackTrace();
        }
        catch(IOException ioe)
        {
            ioe.printStackTrace();
        }
    }
}
    import java.io.Serializable;

public class Computer implements Serializable 
{
    private String brand;
    private double price;
    private int quantity;

    public Computer()
    {
        setBrand("");
        setPrice(0.0);
        setQuantity(0);
    }

    public Computer(String b, double p, int q)
    {
        setBrand(b);
        setPrice(p);
        setQuantity(q);
    }

    public String getBrand()
    {
        return brand;
    }

    public double getPrice()
    {
        return price;
    }

    public int getQuantity()
    {
        return quantity;
    }

    public void setBrand(String b)
    {
        brand = b;
    }

    public void setPrice(double p)
    {
        price = p;
    }

    public void setQuantity(int q)
    {
        quantity = q;
    }

    public String toString()
    {
        return("Brand: "+brand+"\t"+"Price: "+price+"\t"+"Quantity: "+quantity);
    }
}
Was it helpful?

Solution

'Connection reset' usually means you have written to a connection that had already been closed by the peer. In other words, an application protocol error. You've written something that the peer didn't read. The next I/O operation, or a subsequent one depending on buffering, will get 'connection reset'.

In this case the server is writing totalCharge and initializing two ObjectOutputStreams, which both write headers to the stream. The client is only creating one ObjectInputStream, which reads one header, and reads one object, then closes the connection. So the other header is written nowhere and causes the exception.

You can't do this. You can't use multiple ObjectOutputStreams on the same socket, at least not without special care that isn't evident here. You also shouldn't be doing any I/O whatsoever in the accept loop. Move all the client processing to the HandleAClient class, which is what it's for after all, and don't do anything in the accept loop except accept connections and start threads for them.

Also neither your server nor your client is closing the connection. The server is just leaking sockets, and the client is just exiting. The operating system is closing it for you in the client case, but it's poor practice. Close your connections. In this case you should close the ObjectOutputStream.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top