HttpURLConnection和HttpServer之间没有建立连接

时间:2014-12-10 19:33:01

标签: java httpurlconnection httpserver httpconnection

这里的Java过度简化的服务器 - 客户端连接似乎无法正常工作。我已经制作了一台适合浏览器的服务器。我还建立了一个从互联网站点接收数据的http连接。然而,让两人相互交谈似乎很困难。

我有三节课。 Common包含要使用的服务器和客户端类的字符串和数据。

Common.java:

import java.io.Serializable;

public class Common {

    public static class Data implements Serializable{

        private static final long serialVersionUID = 1L;

        public String value = null;

        public Data(String value) {
            this.value = value;
        }
    }

    public static final String PROTOCOL = "http";

    public static final String HOST = "localhost";

    public static final Integer PORT = 39640;

    public static final String PAGE = "/test";

    public static final String POST = "POST";
}

Server.java:

import java.io.IOException;
import java.io.ObjectInputStream;
import java.net.InetAddress;
import java.net.InetSocketAddress;

import com.sun.net.httpserver.*;

@SuppressWarnings("restriction")
public class Server {

    public static class Handler implements HttpHandler {

        @Override
        public void handle(HttpExchange exchange) throws IOException {
            exchange.getResponseHeaders().add("accept", "*/*");
            try {
                ObjectInputStream in = new ObjectInputStream(exchange.getRequestBody());
                Common.Data data = (Common.Data) in.readObject();
                System.out.println(data.value);
                exchange.sendResponseHeaders(200, 0);
                exchange.close();
            } catch(Exception e) {
                exchange.sendResponseHeaders(404, 0);
                exchange.close();
            }           
        }

    }

    public static void main(String[] args) {

        InetSocketAddress socketAddress = null;
        HttpServer server = null;
        try {
            InetAddress address = InetAddress.getByName(Common.HOST);
            socketAddress = new InetSocketAddress(address, Common.PORT);
            server  = HttpServer.create(socketAddress, 10);

            //Add contexts
            server.createContext(Common.PAGE, new Handler());

            server.start();

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

Client.java

import java.io.ObjectOutputStream;
import java.net.HttpURLConnection;
import java.net.URL;


public class Client {

    public static void main(String[] args) {
        try {
            URL url = new URL(Common.PROTOCOL, Common.HOST, Common.PORT, Common.PAGE);
            HttpURLConnection connection = (HttpURLConnection) url.openConnection();

            connection.setRequestMethod(Common.POST);
            connection.setDoOutput(true);
            connection.connect();

            ObjectOutputStream out = new ObjectOutputStream(connection.getOutputStream());
            out.writeObject(new Common.Data("Hello world"));

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

修改 我使用ss -nt来确定连接是否以某种方式发生,即使没有数据传输。


State      Recv-Q Send-Q                      Local Address:Port                        Peer Address:Port 
ESTAB      0      0                               10.0.2.15:46759                      108.168.151.6:80    
ESTAB      0      0                               10.0.2.15:59918                    198.252.206.149:443   
ESTAB      0      0                               127.0.0.1:39030                          127.0.0.1:52906 
ESTAB      0      0                        ::ffff:127.0.0.1:39640                   ::ffff:127.0.0.1:35764
ESTAB      0      0                        ::ffff:127.0.0.1:35764                   ::ffff:127.0.0.1:39640
ESTAB      0      0                        ::ffff:127.0.0.1:52906                   ::ffff:127.0.0.1:39030

2 个答案:

答案 0 :(得分:0)

我在Windows Vista和JDK 1.6.0_10的笔记本电脑上改变了以下几点并且它有效:

共享:

public static final String HOST = "127.0.0.1";
//I´ve changed it to the localhost ip (windows)

服务器,在handle方法中,写一些字符来输出和关闭交换:

 public void handle(final HttpExchange exchange) throws IOException {
        exchange.getResponseHeaders().add("accept", "*/*");
        try {
            final ObjectInputStream in = new ObjectInputStream(exchange.getRequestBody());
            final Common.Data data = (Common.Data) in.readObject();
            System.out.println(data.value);
            exchange.sendResponseHeaders(200, 0);
            exchange.getResponseBody().write("Hello!".getBytes());

        } catch (final Exception e) {
            exchange.sendResponseHeaders(404, 0);
        } finally {
            exchange.close();
        }

在Client类中,我从响应中读取InputStream并将其打印出来:

  public static void main(final String[] args) {
    try {
        final URL url = new URL(Common.PROTOCOL, Common.HOST, Common.PORT, Common.PAGE);
        final HttpURLConnection connection = (HttpURLConnection) url.openConnection();

        connection.setRequestMethod(Common.POST);
        connection.setDoOutput(true);
        connection.connect();

        final ObjectOutputStream out = new ObjectOutputStream(connection.getOutputStream());
        out.writeObject(new Common.Data("Hello world"));
        out.close();
        final BufferedReader reader = new BufferedReader(new InputStreamReader(connection.getInputStream()));
        String line;
        while ((line = reader.readLine()) != null) {
            System.out.println(line);
        }

        connection.disconnect();
    } catch (final Exception e) {
        e.printStackTrace();
    }
}

答案 1 :(得分:0)

除非您获得输入流,错误流或响应代码,否则什么都不会发生。

这是因为在您这样做之前缓冲输出,因此可以准确设置Content-length标头。

您可以使用分块或固定长度传输模式绕过它。