首先感谢orhanobut/logger库的作者提供了这么好用的日志管理工具。Github传送门 本文以orhanobut/logger为基础,通过阅读源码后进行的拓展,为达到以下目的:
logger的基本使用这里笔者就不再阐述了,原文写的非常清楚,首先我们先设置,让Logger将日志打印到本地文件中Logger.addLogAdapter(new DiskLogAdapter());
这时笔者想要对文件大小,文件名字,存储路径等信息做设置,原作者的文档中没有这方面的内容,笔者阅读文档发现也并没有对外提供调用。那么我们只有自己集成LogAdapter实现一套了(DisAdapter也是继承了LogAdapter)。
public class MyDiskLogAdapter implements LogAdapter {
@NonNull
private final MyFormatStrateg formatStrategy;
public MyDiskLogAdapter(){
formatStrategy = MyFormatStrateg.newBuilder().build();
}
@Override
public boolean isLoggable(int priority, @Nullable String tag) {
return true;
}
@Override
public void log(int priority, @Nullable String tag, @NonNull String message) {
formatStrategy.log(priority, tag, message);
}
}
DiskLogAdapter
的构造方法实例了FormatStrateg
,而看FormatStrateg
的源码,我们看到我们需要更改的文件大小等内容都在里面,显然,我们得自己写一个FormatStrateg替换。
@NonNull
public MyFormatStrateg build() {
if (date == null) {
date = new Date();
}
if (dateFormat == null) {
dateFormat = new SimpleDateFormat("yyyy.MM.dd HH:mm:ss.SSS", Locale.UK);
}
if (logStrategy == null) {
String diskPath = Environment.getExternalStorageDirectory().getAbsolutePath();
String folder = diskPath + File.separatorChar + "logger";
HandlerThread ht = new HandlerThread("AndroidFileLogger." + folder);
ht.start();
Handler handler = new MyLogStrategy.WriteHandler(ht.getLooper(), folder, MAX_BYTES);
logStrategy = new MyLogStrategy(handler);
}
return new MyFormatStrateg(this);
}
在FormatStrateg
类中,我们主要看Builder
下的这个build()
方法。这里是对本地log文件的所有文件信息做了一个配置,现在我们就可以任意的修改满足我们自己的需要了。
第一个需求我们满足了,现在我们需要更改Logger写入文件的逻辑,通过阅读源码笔者发现,Logger本身会写入500K的文件log0,当日志装满文件时,会创建一个新的文件log1继续装,最多只会创建两个,并且只要有多个文件,最新的日志会在log1中。这里就和笔者的需求有冲突,日常开发中,笔者希望log0永远是最新的日志,这样笔者上传文件至服务器时只需要考虑上传log0即可,并且最大文件数需求是5个,超过时删除最后一个,创建一个新的log0,另外4个log文件index自动+1。
为实现这个需求,我们需要找到Logger的输出流。在FormatStrateg
中实例了一个叫做LogStrategy
的Handler
就是我们的目标。显然我们既然要更改他,就要自己实现一个。
private File getLogFile(@NonNull String folderName, @NonNull String fileName) {
File folder = new File(folderName);
if (!folder.exists()) {
//TODO: What if folder is not created, what happens then?
folder.mkdirs();
}
String[] files=folder.list();
int filecount=files.length;
File newFile= null;
File existingFile = null;
newFile = new File(folder, String.format("%s_%s.log", fileName, 0));
while (newFile.exists()) {
existingFile = newFile;
newFile = new File(folder, String.format("%s_%s.log", fileName, filecount));
}
if (existingFile != null) {
if (existingFile.length() >= maxFileSize) {
if(filecount>=5){
for(int i=0;i<filecount;i++){
File localfile= new File(folder.getPath()+ File.separator+files[i]);
if(localfile.exists()){
localfile.delete();
}
}
}else{
existingFile.renameTo(newFile);
}
newFile=new File(folder, String.format("%s_%s.log", fileName, 0));
return newFile;
}
return existingFile;
}
return newFile;
}
}
我们直接看核心方法,其实就是一个文件操作,首先判断现有的文件数是否大于我们设置的最大文件数,如果超过,则删除全部文件,新建一个新的文件log0,没有超过就直接创建一个新文件,下标为index+1。同是,我们需要保证最新的log文件时log0,则固定了新文件的名字。主要逻辑跟原作者差别并不大,只是在文件处理这里做了少许改动。
直接将项目中loggerExpand包引入项目,调用'Logger.addLogAdapter(MyDiskLogAdapter())'取代原作者的Logger.addLogAdapter(DiskLogAdapter())
即可,配置文件信息,可以直接在MyFormatStrateg类
中修改。
记得android.permission.WRITE_EXTERNAL_STORAGE
权限很关键!!6.0以上的手机需要动态设置权限。