0

This is my first question here, so I apologize if not every information needed will be in this post.

I'm having problem with communication between java.net.http.HttpClient and HttpServer. I send a request from application with HttpClient to application with Httpserver which the later reads, sends mail according to information in message and sends response to application with HttpClient, either succes if everything is OK or failure if something went wrong.

First few times(it's random how many, sometimes 2 sometimes 24) are usually send correctly and handled correctly by Server which results in httpClient receiving response "success", but suddenly Server gets request with correct header but without body, even though it is always the same one message in request, which results in "failure" response.

My HttpClient:

    private Boolean sendMail(String requestBody) throws IOException, InterruptedException {
    HttpClient client = HttpClient.newBuilder()
            .version(HttpClient.Version.HTTP_1_1)
            .cookieHandler(CookieHandler.getDefault())
            .build();

    HttpRequest request = HttpRequest.newBuilder()
            .uri(URI.create(this.uri))
            .header("Content-Type", "application/json")
            .POST(HttpRequest.BodyPublishers.ofString(requestBody))
            .build();


    //creating response body handler
    HttpResponse.BodyHandler<String> bodyHandler = HttpResponse.BodyHandlers.ofString();


    HttpResponse<String> response = client
            .send(request, bodyHandler);

    String requestOutcome = response.body();
    System.out.println(requestOutcome);

My HttpServer:

   HttpServer server = HttpServer.create(new InetSocketAddress(port), 0);
  ThreadPoolExecutor threadPoolExecutor = (ThreadPoolExecutor) Executors.newFixedThreadPool(10);

  server.createContext("/mial", new  ServerHttpHandler(this.dbHandler, this.mailHandler));
  server.setExecutor(threadPoolExecutor);

  //Start HttpServer
  server.start();

My custom ServerHttpHandler:

 public void handle(HttpExchange httpExchange) throws IOException {
    String requestParamValue=null;
    if("GET".equals(httpExchange.getRequestMethod())) {
        requestParamValue = handleGetRequest(httpExchange);
    }else if("POST".equals(httpExchange.getRequestMethod())) {
        requestParamValue = handlePostRequest(httpExchange);
    }
    handleResponse(httpExchange,requestParamValue);
}
private String handleGetRequest(HttpExchange httpExchange) {
    return httpExchange.
            getRequestURI()
            .toString()
            .split("\\?")[1]
            .split("=")[1];
}

private String handlePostRequest(HttpExchange httpExchange){
    // get request
    Headers reqHeaders = httpExchange.getRequestHeaders();
    reqHeaders.forEach((key, value) -> System.out.println(key + ": " + value));

    String message = null;
    try (InputStream in = httpExchange.getRequestBody()) {
        BufferedReader br = new BufferedReader(new InputStreamReader(in));
        StringBuilder msgbuilder = new StringBuilder();
        while (br.ready()) {
            msgbuilder.append((char) br.read());
        }
        message = msgbuilder.toString();
        System.out.println("Message: " + message);
        br.close();

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

private void handleResponse(HttpExchange httpExchange, String requestParamValue) throws IOException {
    boolean success = this.convertMsgAndSendMail(requestParamValue);

    String htmlResponse = "failure";
    if(success) {
        htmlResponse = "success";
    }

    httpExchange.sendResponseHeaders(200, htmlResponse.length());
    OutputStream outputStream = httpExchange.getResponseBody();

    outputStream.write(htmlResponse.getBytes());
    outputStream.flush();
    outputStream.close();
}

Faulty request:

Connection: [Upgrade, HTTP1_1-Settings]
Http2-settings: [AAEAAEAAAAIAAAABAAMAAABkAAQBAAAAAAUAAEAA]
Host: [localhost:587]
Upgrade: [h2c]
User-agent: [Java-http-client/11.0.6]
Content-type: [application/json]
Content-length: [180]
Message:

So the header is the same every time, but this time I get no message. And as the message is later convert To JSON the only error i get is that message doesn't start with "{" so it isn't Json compatibile.

I searched StackOverflow and other sites for solution to this problem but didn't found any useful tips how to resolve this. Do you have any idea?

daniel
  • 2,665
  • 1
  • 8
  • 18

1 Answers1

0

There are several mistakes here:

  1. When converting bytes to characters (and conversely) you should really always specify a Charset; This is not where your main issue is but you should consider it.
  2. Your while loop is wrong.

You have:

while (br.ready()) {
   msgbuilder.append((char) br.read());
}

what this does is that it will stop reading if a character is not immediately available; what you want is to stop reading when there is no more character to read. This should be something like:

int c;
while ((c = br.read()) > -1) {
    msgbuilder.append((char) c);
}
Dharman
  • 30,962
  • 25
  • 85
  • 135
daniel
  • 2,665
  • 1
  • 8
  • 18