0.效果
1.日志级别的优先级: Verbose (v) < Debug (d) < Info (i) < Warn (w) < Error (e) < Fatal (f)
- 低优先级的日志(如
Verbose和Debug)通常仅在开发和测试环境中启用。 - 高优先级的日志(如
Error和Fatal)则会在生产环境中始终启用,以便监控和排查问题。
2.自定义打印机printer重写log方法 + 时间戳 + 日志过长被截断问题 通常需要在日志加上时间戳前缀,这就需要自定义printer,为每段日志加上时间戳。 如果日志太长,就将它分段,添加到logMessages。
3.去除多余的flutter: 前缀 如果只完成上面2步,会发现日志过长时,虽然分段打印了,但是每一段都有flutter: 前缀。 这是由于Logger库里的日志打印默认用的debugPrint,会加上flutter:前缀。 要去除只能自定义output,使用stout.writeIn()将日志直接写入控制台。
import 'dart:io';
import 'package:logger/logger.dart';
class LogUtil {
static final Logger _logger = Logger(
printer: TimeStampedPrinter(),
output: CustomOutput(),
);
//仅debug模式可见
static void d(String message) {
_logger.d(message);
}
static void i(String message) {
_logger.i(message);
}
static void w(String message) {
_logger.w(message);
}
static void e(String message) {
_logger.e(message);
}
}
class CustomOutput extends LogOutput {
@override
void output(OutputEvent event) {
// 直接将日志写入系统控制台(无flutter: 前缀)
for (final line in event.lines) {
if (line == event.lines.last) {
stdout.writeln(line);
} else {
stdout.write(line);
}
}
}
}
class TimeStampedPrinter extends LogPrinter {
List<String> log(LogEvent event) {
final timestamp = DateTime.now().toIso8601String();
final message = event.message.toString();
//每行最大字符数
const int maxLineLength = 40;
List<String> lines = _splitMessage(message, maxLineLength);
//生成日志:第一行加时间戳,后续行不加
List<String> logMessages = [];
logMessages.add('$timestamp ${event.level}\n');
for (int i = 0; i < lines.length; i++) {
logMessages.add('${lines[i]} ');
}
return logMessages;
}
List<String> _splitMessage(String message, int maxLineLength) {
List<String> multiLineMessage = [];
int start = 0;
while (start < message.length) {
int end = (start + maxLineLength < message.length)
? start + maxLineLength
: message.length;
multiLineMessage.add(message.substring(start, end));
start = end;
}
return multiLineMessage;
}
}