Remove hexdump option in LoggingHandler and dump always
- Allow a user override the log message instead - Prettier hex dump
This commit is contained in:
parent
da9ecadfc0
commit
d5b52077fe
@ -15,6 +15,7 @@
|
||||
*/
|
||||
package io.netty.handler.logging;
|
||||
|
||||
import io.netty.buffer.ChannelBuffer;
|
||||
import io.netty.channel.ChannelBufferHolder;
|
||||
import io.netty.channel.ChannelBufferHolders;
|
||||
import io.netty.channel.ChannelFuture;
|
||||
@ -29,6 +30,7 @@ import io.netty.logging.InternalLogger;
|
||||
import io.netty.logging.InternalLoggerFactory;
|
||||
|
||||
import java.net.SocketAddress;
|
||||
import java.util.Queue;
|
||||
|
||||
/**
|
||||
* A {@link ChannelHandler} that logs all events via {@link InternalLogger}.
|
||||
@ -41,17 +43,17 @@ import java.net.SocketAddress;
|
||||
public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
|
||||
private static final InternalLogLevel DEFAULT_LEVEL = InternalLogLevel.DEBUG;
|
||||
private static final String NEWLINE = String.format("%n");
|
||||
|
||||
private final InternalLogger logger;
|
||||
private final InternalLogLevel level;
|
||||
private final boolean hexDump;
|
||||
|
||||
/**
|
||||
* Creates a new instance whose logger name is the fully qualified class
|
||||
* name of the instance with hex dump enabled.
|
||||
*/
|
||||
public LoggingHandler() {
|
||||
this(true);
|
||||
this(DEFAULT_LEVEL);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -61,36 +63,12 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
* @param level the log level
|
||||
*/
|
||||
public LoggingHandler(InternalLogLevel level) {
|
||||
this(level, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new instance whose logger name is the fully qualified class
|
||||
* name of the instance.
|
||||
*
|
||||
* @param hexDump {@code true} if and only if the hex dump of the received
|
||||
* message is logged
|
||||
*/
|
||||
public LoggingHandler(boolean hexDump) {
|
||||
this(DEFAULT_LEVEL, hexDump);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new instance whose logger name is the fully qualified class
|
||||
* name of the instance.
|
||||
*
|
||||
* @param level the log level
|
||||
* @param hexDump {@code true} if and only if the hex dump of the received
|
||||
* message is logged
|
||||
*/
|
||||
public LoggingHandler(InternalLogLevel level, boolean hexDump) {
|
||||
if (level == null) {
|
||||
throw new NullPointerException("level");
|
||||
}
|
||||
|
||||
logger = InternalLoggerFactory.getInstance(getClass());
|
||||
this.level = level;
|
||||
this.hexDump = hexDump;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -98,17 +76,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
* enabled.
|
||||
*/
|
||||
public LoggingHandler(Class<?> clazz) {
|
||||
this(clazz, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new instance with the specified logger name.
|
||||
*
|
||||
* @param hexDump {@code true} if and only if the hex dump of the received
|
||||
* message is logged
|
||||
*/
|
||||
public LoggingHandler(Class<?> clazz, boolean hexDump) {
|
||||
this(clazz, DEFAULT_LEVEL, hexDump);
|
||||
this(clazz, DEFAULT_LEVEL);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -117,17 +85,6 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
* @param level the log level
|
||||
*/
|
||||
public LoggingHandler(Class<?> clazz, InternalLogLevel level) {
|
||||
this(clazz, level, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new instance with the specified logger name.
|
||||
*
|
||||
* @param level the log level
|
||||
* @param hexDump {@code true} if and only if the hex dump of the received
|
||||
* message is logged
|
||||
*/
|
||||
public LoggingHandler(Class<?> clazz, InternalLogLevel level, boolean hexDump) {
|
||||
if (clazz == null) {
|
||||
throw new NullPointerException("clazz");
|
||||
}
|
||||
@ -136,7 +93,6 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
}
|
||||
logger = InternalLoggerFactory.getInstance(clazz);
|
||||
this.level = level;
|
||||
this.hexDump = hexDump;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -173,7 +129,6 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
}
|
||||
logger = InternalLoggerFactory.getInstance(name);
|
||||
this.level = level;
|
||||
this.hexDump = hexDump;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -192,7 +147,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
return level;
|
||||
}
|
||||
|
||||
protected String message(ChannelHandlerContext ctx, String message) {
|
||||
protected String format(ChannelHandlerContext ctx, String message) {
|
||||
String chStr = ctx.channel().toString();
|
||||
StringBuilder buf = new StringBuilder(chStr.length() + message.length() + 1);
|
||||
buf.append(chStr);
|
||||
@ -201,6 +156,84 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
protected String formatBuffer(String bufName, ChannelBufferHolder<Object> holder) {
|
||||
String content;
|
||||
int size;
|
||||
String elemType;
|
||||
if (holder.hasByteBuffer()) {
|
||||
ChannelBuffer buf = holder.byteBuffer();
|
||||
size = buf.readableBytes();
|
||||
elemType = "Byte";
|
||||
content = hexdump(buf);
|
||||
} else {
|
||||
Queue<Object> buf = holder.messageBuffer();
|
||||
content = buf.toString();
|
||||
size = buf.size();
|
||||
elemType = "Object";
|
||||
}
|
||||
|
||||
return String.format("%s[%s](%d): %s", bufName, elemType, size, content);
|
||||
}
|
||||
|
||||
private static String hexdump(ChannelBuffer buf) {
|
||||
// TODO: Optimize using lookup tables
|
||||
int length = buf.readableBytes();
|
||||
int rows = length / 16 + (length % 15 == 0? 0 : 1) + 4;
|
||||
StringBuilder dump = new StringBuilder(rows * 80);
|
||||
|
||||
dump.append(NEWLINE);
|
||||
dump.append(" +-------------------------------------------------+");
|
||||
dump.append(NEWLINE);
|
||||
dump.append(" | 0 1 2 3 4 5 6 7 8 9 a b c d e f |");
|
||||
dump.append(NEWLINE);
|
||||
dump.append("+--------+-------------------------------------------------+----------------+");
|
||||
|
||||
int i;
|
||||
for (i = buf.readerIndex(); i < buf.writerIndex(); i ++) {
|
||||
int relIdx = i - buf.readerIndex();
|
||||
int relIdxMod16 = relIdx & 15;
|
||||
if (relIdxMod16 == 0) {
|
||||
dump.append(NEWLINE);
|
||||
dump.append(String.format("|%8x|", relIdx));
|
||||
}
|
||||
dump.append(String.format(" %02x", buf.getUnsignedByte(i)));
|
||||
if (relIdxMod16 == 15) {
|
||||
dump.append(" |");
|
||||
for (int j = i - 15; j <= i; j ++) {
|
||||
dump.append(toChar(buf.getByte(j)));
|
||||
}
|
||||
dump.append('|');
|
||||
}
|
||||
}
|
||||
if ((i - buf.readerIndex() & 15) != 0) {
|
||||
int remainder = length & 15;
|
||||
for (int j = 16 - remainder; j > 0; j --) {
|
||||
dump.append(" ");
|
||||
}
|
||||
dump.append(" |");
|
||||
for (int j = i - remainder; j < i; j ++) {
|
||||
dump.append(toChar(buf.getByte(j)));
|
||||
}
|
||||
for (int j = 16 - remainder; j > 0; j --) {
|
||||
dump.append(' ');
|
||||
}
|
||||
dump.append('|');
|
||||
}
|
||||
|
||||
dump.append(NEWLINE);
|
||||
dump.append("+--------+-------------------------------------------------+----------------+");
|
||||
return dump.toString();
|
||||
}
|
||||
|
||||
private static char toChar(int ch) {
|
||||
ch = ch & 0xff;
|
||||
if (ch <= 0x1f || ch >= 0x7f) {
|
||||
return '.';
|
||||
} else {
|
||||
return (char) ch;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChannelBufferHolder<Object> newOutboundBuffer(
|
||||
ChannelOutboundHandlerContext<Object> ctx) throws Exception {
|
||||
@ -217,7 +250,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void channelRegistered(ChannelInboundHandlerContext<Object> ctx)
|
||||
throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "REGISTERED"));
|
||||
logger.log(level, format(ctx, "REGISTERED"));
|
||||
}
|
||||
super.channelRegistered(ctx);
|
||||
}
|
||||
@ -226,7 +259,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void channelUnregistered(ChannelInboundHandlerContext<Object> ctx)
|
||||
throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "UNREGISTERED"));
|
||||
logger.log(level, format(ctx, "UNREGISTERED"));
|
||||
}
|
||||
super.channelUnregistered(ctx);
|
||||
}
|
||||
@ -235,7 +268,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void channelActive(ChannelInboundHandlerContext<Object> ctx)
|
||||
throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "ACTIVE"));
|
||||
logger.log(level, format(ctx, "ACTIVE"));
|
||||
}
|
||||
super.channelActive(ctx);
|
||||
}
|
||||
@ -244,7 +277,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void channelInactive(ChannelInboundHandlerContext<Object> ctx)
|
||||
throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "INACTIVE"));
|
||||
logger.log(level, format(ctx, "INACTIVE"));
|
||||
}
|
||||
super.channelInactive(ctx);
|
||||
}
|
||||
@ -253,7 +286,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void exceptionCaught(ChannelInboundHandlerContext<Object> ctx,
|
||||
Throwable cause) throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, String.format("EXCEPTION: %s", cause)), cause);
|
||||
logger.log(level, format(ctx, String.format("EXCEPTION: %s", cause)), cause);
|
||||
}
|
||||
super.exceptionCaught(ctx, cause);
|
||||
}
|
||||
@ -262,7 +295,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void userEventTriggered(ChannelInboundHandlerContext<Object> ctx,
|
||||
Object evt) throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, String.format("USER_EVENT: %s", evt)));
|
||||
logger.log(level, format(ctx, String.format("USER_EVENT: %s", evt)));
|
||||
}
|
||||
super.userEventTriggered(ctx, evt);
|
||||
}
|
||||
@ -271,17 +304,16 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void inboundBufferUpdated(ChannelInboundHandlerContext<Object> ctx)
|
||||
throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "INBOUND_UPDATED"));
|
||||
logger.log(level, format(ctx, formatBuffer("INBUF", ctx.in())));
|
||||
}
|
||||
// TODO Auto-generated method stub
|
||||
super.inboundBufferUpdated(ctx);
|
||||
ctx.fireInboundBufferUpdated();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bind(ChannelOutboundHandlerContext<Object> ctx,
|
||||
SocketAddress localAddress, ChannelFuture future) throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, String.format("bind(%s)", localAddress)));
|
||||
logger.log(level, format(ctx, String.format("bind(%s)", localAddress)));
|
||||
}
|
||||
super.bind(ctx, localAddress, future);
|
||||
}
|
||||
@ -291,7 +323,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
SocketAddress remoteAddress, SocketAddress localAddress,
|
||||
ChannelFuture future) throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, String.format("connect(%s, %s)", remoteAddress, localAddress)));
|
||||
logger.log(level, format(ctx, String.format("connect(%s, %s)", remoteAddress, localAddress)));
|
||||
}
|
||||
super.connect(ctx, remoteAddress, localAddress, future);
|
||||
}
|
||||
@ -300,7 +332,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void disconnect(ChannelOutboundHandlerContext<Object> ctx,
|
||||
ChannelFuture future) throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "disconnect()"));
|
||||
logger.log(level, format(ctx, "disconnect()"));
|
||||
}
|
||||
super.disconnect(ctx, future);
|
||||
}
|
||||
@ -309,7 +341,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void close(ChannelOutboundHandlerContext<Object> ctx,
|
||||
ChannelFuture future) throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "close()"));
|
||||
logger.log(level, format(ctx, "close()"));
|
||||
}
|
||||
super.close(ctx, future);
|
||||
}
|
||||
@ -318,7 +350,7 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void deregister(ChannelOutboundHandlerContext<Object> ctx,
|
||||
ChannelFuture future) throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "deregister()"));
|
||||
logger.log(level, format(ctx, "deregister()"));
|
||||
}
|
||||
super.deregister(ctx, future);
|
||||
}
|
||||
@ -327,9 +359,8 @@ public class LoggingHandler extends ChannelHandlerAdapter<Object, Object> {
|
||||
public void flush(ChannelOutboundHandlerContext<Object> ctx,
|
||||
ChannelFuture future) throws Exception {
|
||||
if (getLogger().isEnabled(level)) {
|
||||
logger.log(level, message(ctx, "flush()"));
|
||||
logger.log(level, format(ctx, "flush()"));
|
||||
}
|
||||
super.flush(ctx, future);
|
||||
}
|
||||
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user