veilidchat/lib/tools/loggy.dart
Christien Rioux 31f562119a checkpoint
2024-01-04 22:29:43 -05:00

158 lines
3.5 KiB
Dart

import 'dart:io' show Platform;
import 'package:ansicolor/ansicolor.dart';
import 'package:bloc/bloc.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter_translate/flutter_translate.dart';
import 'package:intl/intl.dart';
import 'package:loggy/loggy.dart';
import 'package:veilid_support/veilid_support.dart';
import '../veilid_processor/views/developer.dart';
import 'state_logger.dart';
String wrapWithLogColor(LogLevel? level, String text) {
// XXX: https://github.com/flutter/flutter/issues/64491
if (!kIsWeb && Platform.isIOS) {
return text;
}
if (level == null) {
return text;
}
final pen = AnsiPen();
ansiColorDisabled = false;
switch (level) {
case LogLevel.error:
pen
..reset()
..red(bold: true);
return pen(text);
case LogLevel.warning:
pen
..reset()
..yellow(bold: true);
return pen(text);
case LogLevel.info:
pen
..reset()
..white(bold: true);
return pen(text);
case LogLevel.debug:
pen
..reset()
..green(bold: true);
return pen(text);
case traceLevel:
pen
..reset()
..blue(bold: true);
return pen(text);
}
return text;
}
final DateFormat _dateFormatter = DateFormat('HH:mm:ss.SSS');
extension PrettyPrintLogRecord on LogRecord {
String pretty() {
final tm = _dateFormatter.format(time.toLocal());
final lev = logLevelEmoji(level);
final lstr = wrapWithLogColor(level, tm);
return '$lstr $lev $message';
}
}
List<LogLevel> logLevels = [
LogLevel.error,
LogLevel.warning,
LogLevel.info,
LogLevel.debug,
traceLevel,
];
String logLevelName(LogLevel logLevel) {
switch (logLevel) {
case traceLevel:
return translate('log.trace');
case LogLevel.debug:
return translate('log.debug');
case LogLevel.info:
return translate('log.info');
case LogLevel.warning:
return translate('log.warning');
case LogLevel.error:
return translate('log.error');
}
return '???';
}
String logLevelEmoji(LogLevel logLevel) {
switch (logLevel) {
case traceLevel:
return '👾';
case LogLevel.debug:
return '🐛';
case LogLevel.info:
return '💡';
case LogLevel.warning:
return '🍋';
case LogLevel.error:
return '🛑';
}
return '';
}
class CallbackPrinter extends LoggyPrinter {
CallbackPrinter() : super();
void Function(LogRecord)? callback;
@override
void onLog(LogRecord record) {
final out = record.pretty();
debugPrint(out);
globalDebugTerminal.write('$out\n'.replaceAll('\n', '\r\n'));
callback?.call(record);
}
void setCallback(void Function(LogRecord)? cb) {
callback = cb;
}
}
CallbackPrinter globalTerminalPrinter = CallbackPrinter();
LogOptions getLogOptions(LogLevel? level) => LogOptions(
level ?? LogLevel.all,
stackTraceLevel: LogLevel.error,
);
class RootLoggy implements LoggyType {
@override
Loggy<RootLoggy> get loggy => Loggy<RootLoggy>('');
}
Loggy get log => Loggy<RootLoggy>('veilidchat');
void initLoggy() {
Loggy.initLoggy(
logPrinter: globalTerminalPrinter,
logOptions: getLogOptions(null),
);
// ignore: do_not_use_environment
const isTrace = String.fromEnvironment('LOG_TRACE') != '';
LogLevel logLevel;
if (isTrace) {
logLevel = traceLevel;
} else {
logLevel = kDebugMode ? LogLevel.debug : LogLevel.info;
}
Loggy('').level = getLogOptions(logLevel);
// Create state logger
Bloc.observer = const StateLogger();
}