今天终于遇到了log4j配置成DailyRollingFileAppender后,没有正确生成文件,或者没有重命名log文件
在网上寻找了一遍,绝大部分都是复制了了就不管了,大致原文该链接[url]http://www.blogjava.net/DreamAngel/archive/2011/11/10/363400.html[/url]中的代码有明显问题,比如日志文件过大怎么办,然而复制了原log文件后,那原来的log文件需要清空却没有做。
现修正如下,但修正的结果却是错误的(你可以不看修正的结果了):
真正占用文件的根源可以从这里说起,windows平台下你打开一个记事本,你是可以删除的该记事本的,但是如果用独占的方式打开一个记事本,因为加了锁,而另一个进程(对头这里是进程,而非线程)却要去重命名它,怎么可能做到呢,所以最好是两个独立的进程就做独立进程的事情了,具体解决思路当然是进程既然是独立的,log4j.properties中一定要修改日志记录的路径为不同的进程所独有。
在网上寻找了一遍,绝大部分都是复制了了就不管了,大致原文该链接[url]http://www.blogjava.net/DreamAngel/archive/2011/11/10/363400.html[/url]中的代码有明显问题,比如日志文件过大怎么办,然而复制了原log文件后,那原来的log文件需要清空却没有做。
现修正如下,但修正的结果却是错误的(你可以不看修正的结果了):
真正占用文件的根源可以从这里说起,windows平台下你打开一个记事本,你是可以删除的该记事本的,但是如果用独占的方式打开一个记事本,因为加了锁,而另一个进程(对头这里是进程,而非线程)却要去重命名它,怎么可能做到呢,所以最好是两个独立的进程就做独立进程的事情了,具体解决思路当然是进程既然是独立的,log4j.properties中一定要修改日志记录的路径为不同的进程所独有。
/**
* Rollover the current file to a new file.
*/
void rollOver() throws IOException {
/* Compute filename, but only if datePattern is specified */
if (datePattern == null) {
errorHandler.error("Missing DatePattern option in rollOver().");
return;
}
String datedFilename = fileName + sdf.format(now);
// It is too early to roll over because we are still within the
// bounds of the current interval. Rollover will occur once the
// next interval is reached.
if (scheduledFilename.equals(datedFilename)) {
return;
}
// close current file, and rename it to datedFilename
this.closeFile();
File target = new File(scheduledFilename);
if (target.exists()) {
target.delete();
}
File file = new File(fileName);
boolean result = copy(file, target);
if (result) {
FileWriter fw = new FileWriter(file);
fw.write("");
fw.flush();
fw.close();
LogLog.debug(fileName + " -> " + scheduledFilename);
} else {
LogLog.error("Failed to rename [" + fileName + "] to ["
+ scheduledFilename + "].");
}
try {
// This will also close the file. This is OK since multiple
// close operations are safe.
this.setFile(fileName, true, this.bufferedIO, this.bufferSize);
} catch (IOException e) {
errorHandler.error("setFile(" + fileName + ", true) call failed.");
}
scheduledFilename = datedFilename;
}
// 最大的流为60MB,当文件的容量大于60MB的时候便分开流
final int MAX_BYTE = 60000000;
/**
* Copies src file to dst file. If the dst file does not exist, it is
* created.8KB cache
*
* @param src
* @param dst
* @throws IOException
*/
boolean copy(File src, File dst) throws IOException {
try {
long streamTotal = 0; // 接受流的容量
int streamNum = 0; // 流需要分开的数量
int leave = 0; // 文件剩下的字符数
byte[] inOutb;// byte数组接受文件的数据
FileInputStream in = new FileInputStream(src);
FileOutputStream out = new FileOutputStream(dst);
// 通过available方法取得流的最大字符数
streamTotal = in.available();
// 取得流文件需要分开的数量
streamNum = (int)Math.floor(streamTotal/MAX_BYTE);
// 分开文件之后,剩余的数量
leave = (int)(streamTotal % MAX_BYTE);
// 文件的容量大于60MB时进入循环
if(streamNum>0){
for (int i = 0; i < streamNum; i++) {
inOutb = new byte[MAX_BYTE];
// 读入流,保存在byte数组
in.read(inOutb, 0, MAX_BYTE);
out.write(inOutb);
out.flush();
}
}
// 剩余的流数据
inOutb = new byte[leave];
in.read(inOutb, 0, leave);
out.write(inOutb);
out.flush();
in.close();
out.close();
return true;
} catch (FileNotFoundException e) {
LogLog.error("源文件不存在,或者目标文件无法被识别.");
return false;
} catch (IOException e) {
LogLog.error("文件读写错误.");
return false;
}
}