* I2PTunnel:

- Better logging of server errors
      - Return 503 to client before closing i2p socket if server is not there
This commit is contained in:
zzz
2010-12-03 16:51:04 +00:00
parent ae6a6a1d9c
commit 5c73a60551
3 changed files with 39 additions and 21 deletions

View File

@@ -37,6 +37,19 @@ public class I2PTunnelHTTPServer extends I2PTunnelServer {
private static final String DEST64_HEADER = "X-I2P-DestB64";
private static final String DEST32_HEADER = "X-I2P-DestB32";
private final static byte[] ERR_UNAVAILABLE =
("HTTP/1.1 503 Service Unavailable\r\n"+
"Content-Type: text/html; charset=iso-8859-1\r\n"+
"Cache-control: no-cache\r\n"+
"Connection: close\r\n"+
"Proxy-Connection: close\r\n"+
"\r\n"+
"<html><head><title>503 Service Unavailable<title></head>\n"+
"<body><h2>503 Service Unavailable</h2>\n" +
"<p>This I2P eepsite is unavailable. It may be down or undergoing maintenance.</p>\n" +
"</body></html>")
.getBytes();
public I2PTunnelHTTPServer(InetAddress host, int port, String privData, String spoofHost, Logging l, EventDispatcher notifyThis, I2PTunnel tunnel) {
super(host, port, privData, l, notifyThis, tunnel);
setupI2PTunnelHTTPServer(spoofHost);
@@ -124,12 +137,16 @@ public class I2PTunnelHTTPServer extends I2PTunnelServer {
new I2PTunnelRunner(s, socket, slock, null, modifiedHeader.getBytes(), null);
}
} catch (SocketException ex) {
try {
// Send a 503, so the user doesn't get an HTTP Proxy error message
// and blame his router or the network.
socket.getOutputStream().write(ERR_UNAVAILABLE);
} catch (IOException ioe) {}
try {
socket.close();
} catch (IOException ioe) {
} catch (IOException ioe) {}
if (_log.shouldLog(Log.ERROR))
_log.error("Error while closing the received i2p con", ex);
}
_log.error("Error connecting to HTTP server " + remoteHost + ':' + remotePort, ex);
} catch (IOException ex) {
try {
socket.close();
@@ -148,7 +165,8 @@ public class I2PTunnelHTTPServer extends I2PTunnelServer {
long timeToHandle = afterHandle - afterAccept;
getTunnel().getContext().statManager().addRateData("i2ptunnel.httpserver.blockingHandleTime", timeToHandle, 0);
if ( (timeToHandle > 1000) && (_log.shouldLog(Log.WARN)) )
_log.warn("Took a while to handle the request [" + timeToHandle + ", socket create: " + (afterSocket-afterAccept) + "]");
_log.warn("Took a while to handle the request for " + remoteHost + ':' + remotePort +
" [" + timeToHandle + ", socket create: " + (afterSocket-afterAccept) + "]");
}
private static class CompressedRequestor implements Runnable {

View File

@@ -123,12 +123,12 @@ public class I2PTunnelIRCServer extends I2PTunnelServer implements Runnable {
Socket s = new Socket(remoteHost, remotePort);
new I2PTunnelRunner(s, socket, slock, null, modifiedRegistration.getBytes(), null);
} catch (SocketException ex) {
// TODO send the equivalent of a 503?
try {
socket.close();
} catch (IOException ioe) {
} catch (IOException ioe) {}
if (_log.shouldLog(Log.ERROR))
_log.error("Error while closing the received i2p con", ex);
}
_log.error("Error connecting to IRC server " + remoteHost + ':' + remotePort, ex);
} catch (IOException ex) {
try {
socket.close();

View File

@@ -68,7 +68,7 @@ public class I2PTunnelServer extends I2PTunnelTask implements Runnable {
super("Server at " + host + ':' + port, notifyThis, tunnel);
_log = tunnel.getContext().logManager().getLog(getClass());
ByteArrayInputStream bais = new ByteArrayInputStream(Base64.decode(privData));
SetUsePool(tunnel);
setUsePool(tunnel);
init(host, port, bais, privData, l);
}
@@ -80,7 +80,7 @@ public class I2PTunnelServer extends I2PTunnelTask implements Runnable {
EventDispatcher notifyThis, I2PTunnel tunnel) {
super("Server at " + host + ':' + port, notifyThis, tunnel);
_log = tunnel.getContext().logManager().getLog(getClass());
SetUsePool(tunnel);
setUsePool(tunnel);
FileInputStream fis = null;
try {
fis = new FileInputStream(privkey);
@@ -101,13 +101,13 @@ public class I2PTunnelServer extends I2PTunnelTask implements Runnable {
public I2PTunnelServer(InetAddress host, int port, InputStream privData, String privkeyname, Logging l, EventDispatcher notifyThis, I2PTunnel tunnel) {
super("Server at " + host + ':' + port, notifyThis, tunnel);
_log = tunnel.getContext().logManager().getLog(getClass());
SetUsePool(tunnel);
setUsePool(tunnel);
init(host, port, privData, privkeyname, l);
}
private void SetUsePool(I2PTunnel Tunnel) {
String usePool = Tunnel.getClientOptions().getProperty("i2ptunnel.usePool");
private void setUsePool(I2PTunnel tunnel) {
String usePool = tunnel.getClientOptions().getProperty("i2ptunnel.usePool");
if (usePool != null)
_usePool = "true".equalsIgnoreCase(usePool);
else
@@ -269,15 +269,14 @@ public class I2PTunnelServer extends I2PTunnelTask implements Runnable {
}
public void run() {
if (shouldUsePool()) {
I2PServerSocket i2pS_S = sockMgr.getServerSocket();
if (shouldUsePool()) {
int handlers = getHandlerCount();
for (int i = 0; i < handlers; i++) {
I2PAppThread handler = new I2PAppThread(new Handler(i2pS_S), "Handle Server " + i);
handler.start();
}
} else {
I2PServerSocket i2pS_S = sockMgr.getServerSocket();
while (true) {
try {
final I2PSocket i2ps = i2pS_S.accept();
@@ -340,17 +339,18 @@ public class I2PTunnelServer extends I2PTunnelTask implements Runnable {
} catch (SocketException ex) {
try {
socket.close();
} catch (IOException ioe) {
_log.error("Error while closing the received i2p con", ex);
}
} catch (IOException ioe) {}
if (_log.shouldLog(Log.ERROR))
_log.error("Error connecting to server " + remoteHost + ':' + remotePort, ex);
} catch (IOException ex) {
_log.error("Error while waiting for I2PConnections", ex);
}
long afterHandle = I2PAppContext.getGlobalContext().clock().now();
long timeToHandle = afterHandle - afterAccept;
if (timeToHandle > 1000)
_log.warn("Took a while to handle the request [" + timeToHandle + ", socket create: " + (afterSocket-afterAccept) + "]");
if ( (timeToHandle > 1000) && (_log.shouldLog(Log.WARN)) )
_log.warn("Took a while to handle the request for " + remoteHost + ':' + remotePort +
" [" + timeToHandle + ", socket create: " + (afterSocket-afterAccept) + "]");
}
}