爲了能夠記錄和跟蹤一些事件,我已經爲我的Java項目添加了一個LoggingHandler類。在這個類的內部,我使用了兩個不同的log4j記錄器實例 - 一個用於記錄事件,另一個用於將事件追蹤到不同的文件中。類的初始化塊看起來是這樣的:Log4j:事件出現在錯誤的日誌文件中
public void initialize()
{
System.out.print("starting logging server ...");
// create logger instances
logLogger = Logger.getLogger("log");
traceLogger = Logger.getLogger("trace");
// create pattern layout
String conversionPattern = "%c{2} %d{ABSOLUTE} %r %p %m%n";
try
{
patternLayout = new PatternLayout();
patternLayout.setConversionPattern(conversionPattern);
}
catch (Exception e)
{
System.out.println("error: could not create logger layout pattern");
System.out.println(e);
System.exit(1);
}
// add pattern to file appender
try
{
logFileAppender = new FileAppender(patternLayout, logFilename, false);
traceFileAppender = new FileAppender(patternLayout, traceFilename, false);
}
catch (IOException e)
{
System.out.println("error: could not add logger layout pattern to corresponding appender");
System.out.println(e);
System.exit(1);
}
// add appenders to loggers
logLogger.addAppender(logFileAppender);
traceLogger.addAppender(traceFileAppender);
// set logger level
logLogger.setLevel(Level.INFO);
traceLogger.setLevel(Level.INFO);
// start logging server
loggingServer = new LoggingServer(logLogger, traceLogger, serverPort, this);
loggingServer.start();
System.out.println(" done");
}
要確保只有唯一的線程在同一時間使用日誌記錄器實例的功能/跟蹤的方法調用.INFO的測井方法()內一個同步塊。一個例子是這樣的:
public void logMessage(String message)
{
synchronized (logLogger)
{
if (logLogger.isInfoEnabled() && logFileAppender != null)
{
logLogger.info(instanceName + ": " + message);
}
}
}
如果看我的日誌文件,我看到,有時候一個事件出現在了錯誤的文件。舉個例子:
trace 10:41:30,773 11080 INFO masterControl(192.168.2.21): string broadcast message was pushed from 1267093 to vehicle 1055293 (slaveControl 1)
trace 10:41:30,784 11091 INFO masterControl(192.168.2.21): string broadcast message was pushed from 1156513 to vehicle 1105792 (slaveControl 1)
trace 10:41:30,796 11103 INFO masterControl(192.168.2.21): string broadcast message was pushed from 1104306 to vehicle 1055293 (slaveControl 1)
trace 10:41:30,808 11115 INFO masterControl(192.168.2.21): vehicle 1327879 was pushed to slave control 1
10:41:30,808 11115 INFO masterControl(192.168.2.21): string broadcast message was pushed from 1101572 to vehicle 106741 (slaveControl 1)
trace 10:41:30,820 11127 INFO masterControl(192.168.2.21): string broadcast message was pushed from 1055293 to vehicle 1104306 (slaveControl 1)
我覺得現在的問題occures每次兩個事件發生在同一時間(這裏:10:41:30808)。有人有一個想法如何解決我的問題?我已經嘗試過的方法調用後添加一個sleep(),但這並沒有幫助...
BR,
馬庫斯
編輯:
logtrace 11:16:07,75511:16:07,755 1129711297 INFOINFO masterControl(192.168.2.21): string broadcast message was pushed from 1291400 to vehicle 1138272 (slaveControl 1)masterControl(192.168.2.21): vehicle 1333770 was added to slave control 1
或
log 11:16:08,562 12104 INFO 11:16:08,562 masterControl(192.168.2.21): string broadcast message was pushed from 117772 to vehicle 1217744 (slaveControl 1)
12104 INFO masterControl(192.168.2.21):車輛1169775被推到從屬控制1
編輯2:
好像(使用我的客戶機/服務器交換信息RMI連接)如果測井方法是從RMI線程中調用僅出現問題。 ...
編輯3:
我自己解決了這個問題:它看起來像log4j的不完全螺紋保存。在使用單獨的對象同步所有日誌/跟蹤方法後,所有工作都正常。在寫入文件之前,lib可能會將消息寫入線程不安全的緩衝區?
如果輸出流意味着appender,Appenders是線程安全的:'doAppend'方法是'synchronized'。 – 2009-08-28 09:23:29
在fileAppeners上同步後,問題仍然存在(請參閱上面的示例)。也許我必須把記錄器實例放到不同的線程中? – Markus 2009-08-28 09:25:08
不,你可以在初始化方法中看到兩個appender綁定到不同的文件(logFilename&traceFilename),但它們使用的是相同的patternLayout。 有些分鐘agao我試圖將日誌/跟蹤移動到不同的線程,但這也沒有幫助。 – Markus 2009-08-28 11:54:57