8223714: HTTPSetAuthenticatorTest could be made more resilient

HTTPTestServer (in the test infrastructure) will no longer stop accepting requests if a previous request processing failed

Reviewed-by: dfuchs
This commit is contained in:
Jaikiran Pai 2019-08-30 17:22:55 +05:30
parent 47e005582b
commit 6b2e444aa1

View File

@ -980,6 +980,8 @@ public class HTTPTestServer extends HTTPTest {
implements Runnable { implements Runnable {
final ServerSocket ss; final ServerSocket ss;
private volatile boolean stop;
public HttpsProxyTunnel(HttpServer server, HTTPTestServer target, public HttpsProxyTunnel(HttpServer server, HTTPTestServer target,
HttpHandler delegate) HttpHandler delegate)
throws IOException { throws IOException {
@ -998,9 +1000,10 @@ public class HTTPTestServer extends HTTPTest {
@Override @Override
public void stop() { public void stop() {
try (var toClose = ss) {
stop = true;
System.out.println("Server " + ss + " stop requested");
super.stop(); super.stop();
try {
ss.close();
} catch (IOException ex) { } catch (IOException ex) {
if (DEBUG) ex.printStackTrace(System.out); if (DEBUG) ex.printStackTrace(System.out);
} }
@ -1050,6 +1053,9 @@ public class HTTPTestServer extends HTTPTest {
if (c == '\n') break; if (c == '\n') break;
b.appendCodePoint(c); b.appendCodePoint(c);
} }
if (b.length() == 0) {
return "";
}
if (b.codePointAt(b.length() -1) == '\r') { if (b.codePointAt(b.length() -1) == '\r') {
b.delete(b.length() -1, b.length()); b.delete(b.length() -1, b.length());
} }
@ -1059,21 +1065,73 @@ public class HTTPTestServer extends HTTPTest {
@Override @Override
public void run() { public void run() {
Socket clientConnection = null; Socket clientConnection = null;
try { while (!stop) {
while (true) {
System.out.println("Tunnel: Waiting for client at: " + ss); System.out.println("Tunnel: Waiting for client at: " + ss);
Socket previous = clientConnection; final Socket previous = clientConnection;
try { try {
clientConnection = ss.accept(); clientConnection = ss.accept();
} catch (IOException io) { } catch (IOException io) {
if (DEBUG) io.printStackTrace(System.out); try {
ss.close();
} catch (IOException ex) {
if (DEBUG) {
ex.printStackTrace(System.out);
}
}
// log the reason that caused the server to stop accepting connections
if (!stop) {
System.err.println("Server will stop accepting connections due to an exception:");
io.printStackTrace();
}
break; break;
} finally { } finally {
// close the previous connection // close the previous connection
if (previous != null) previous.close(); if (previous != null) {
try {
previous.close();
} catch (IOException e) {
// ignore
if (DEBUG) {
System.out.println("Ignoring exception that happened while closing " +
"an older connection:");
e.printStackTrace(System.out);
}
}
}
} }
System.out.println("Tunnel: Client accepted"); System.out.println("Tunnel: Client accepted");
Socket targetConnection = null; try {
// We have only 1 client... process the current client
// request and wait until it has finished before
// accepting a new connection request.
processRequestAndWaitToComplete(clientConnection);
} catch (IOException ioe) {
// close the client connection
try {
clientConnection.close();
} catch (IOException io) {
// ignore
if (DEBUG) {
System.out.println("Ignoring exception that happened during client" +
" connection close:");
io.printStackTrace(System.out);
}
} finally {
clientConnection = null;
}
} catch (Throwable t) {
// don't close the client connection for non-IOExceptions, instead
// just log it and move on to accept next connection
if (!stop) {
t.printStackTrace();
}
}
}
}
private void processRequestAndWaitToComplete(final Socket clientConnection)
throws IOException, InterruptedException {
final Socket targetConnection;
InputStream ccis = clientConnection.getInputStream(); InputStream ccis = clientConnection.getInputStream();
OutputStream ccos = clientConnection.getOutputStream(); OutputStream ccos = clientConnection.getOutputStream();
Writer w = new OutputStreamWriter( Writer w = new OutputStreamWriter(
@ -1104,10 +1162,11 @@ public class HTTPTestServer extends HTTPTest {
pw.print("HTTP/1.1 200 OK\r\nContent-Length: 0\r\n\r\n"); pw.print("HTTP/1.1 200 OK\r\nContent-Length: 0\r\n\r\n");
pw.flush(); pw.flush();
} else { } else {
// This should not happen. If it does let our serverImpl // This should not happen. If it does then consider it a
// deal with it. // client error and throw an IOException
throw new IOException("Tunnel: Unexpected status line: " System.out.println("Tunnel: Throwing an IOException due to unexpected" +
+ requestLine); " request line: " + requestLine);
throw new IOException("Client request error - Unexpected request line");
} }
// Pipe the input stream of the client connection to the // Pipe the input stream of the client connection to the
@ -1118,21 +1177,9 @@ public class HTTPTestServer extends HTTPTest {
Thread t2 = pipe(targetConnection.getInputStream(), ccos, '-'); Thread t2 = pipe(targetConnection.getInputStream(), ccos, '-');
t1.start(); t1.start();
t2.start(); t2.start();
// wait for the request to complete
// We have only 1 client... wait until it has finished before
// accepting a new connection request.
t1.join(); t1.join();
t2.join(); t2.join();
} }
} catch (Throwable ex) {
try {
ss.close();
} catch (IOException ex1) {
ex.addSuppressed(ex1);
}
ex.printStackTrace(System.err);
}
}
} }
} }