mirror of
https://github.com/Yubico/yubioath-flutter.git
synced 2024-11-30 09:47:43 +03:00
110 lines
3.1 KiB
Dart
Executable File
110 lines
3.1 KiB
Dart
Executable File
// ignore_for_file: constant_identifier_names
|
|
|
|
import 'package:flutter/material.dart';
|
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
|
import 'package:logging/logging.dart';
|
|
|
|
String _pad(int value, int zeroes) => value.toString().padLeft(zeroes, '0');
|
|
|
|
extension DateTimeFormat on DateTime {
|
|
String get logFormat =>
|
|
'${_pad(hour, 2)}:${_pad(minute, 2)}:${_pad(second, 2)}.${_pad(millisecond, 3)}';
|
|
}
|
|
|
|
class Levels {
|
|
/// Key for tracing information ([value] = 500).
|
|
static const Level TRAFFIC = Level('TRAFFIC', 500);
|
|
|
|
/// Key for static configuration messages ([value] = 700).
|
|
static const Level DEBUG = Level('DEBUG', 700);
|
|
|
|
/// Key for informational messages ([value] = 800).
|
|
static const Level INFO = Level.INFO;
|
|
|
|
/// Key for potential problems ([value] = 900).
|
|
static const Level WARNING = Level.WARNING;
|
|
|
|
/// Key for serious failures ([value] = 1000).
|
|
static const Level ERROR = Level('ERROR', 1000);
|
|
|
|
static const List<Level> LEVELS = [
|
|
TRAFFIC,
|
|
DEBUG,
|
|
INFO,
|
|
WARNING,
|
|
ERROR,
|
|
];
|
|
}
|
|
|
|
extension LoggerExt on Logger {
|
|
void error(Object? message, [Object? error, StackTrace? stackTrace]) =>
|
|
log(Levels.ERROR, message, error, stackTrace);
|
|
void debug(Object? message, [Object? error, StackTrace? stackTrace]) =>
|
|
log(Levels.DEBUG, message, error, stackTrace);
|
|
void traffic(Object? message, [Object? error, StackTrace? stackTrace]) =>
|
|
log(Levels.TRAFFIC, message, error, stackTrace);
|
|
}
|
|
|
|
final logLevelProvider =
|
|
StateNotifierProvider<LogLevelNotifier, Level>((ref) => LogLevelNotifier());
|
|
|
|
class LogLevelNotifier extends StateNotifier<Level> {
|
|
final List<String> _buffer = [];
|
|
LogLevelNotifier() : super(Logger.root.level) {
|
|
Logger.root.onRecord.listen((record) {
|
|
_buffer.add(
|
|
'${record.time.logFormat} [${record.loggerName}] ${record.level}: ${record.message}');
|
|
if (record.error != null) {
|
|
_buffer.add('${record.error}');
|
|
}
|
|
while (_buffer.length > 1000) {
|
|
_buffer.removeAt(0);
|
|
}
|
|
});
|
|
}
|
|
|
|
void setLogLevel(Level level) {
|
|
state = level;
|
|
Logger.root.level = level;
|
|
}
|
|
|
|
Future<List<String>> getLogs() async {
|
|
return List.unmodifiable(_buffer);
|
|
}
|
|
}
|
|
|
|
class LogWarningOverlay extends StatelessWidget {
|
|
final Widget child;
|
|
|
|
const LogWarningOverlay({super.key, required this.child});
|
|
|
|
@override
|
|
Widget build(BuildContext context) {
|
|
return Stack(
|
|
alignment: Alignment.center,
|
|
children: [
|
|
child,
|
|
Consumer(builder: (context, ref, _) {
|
|
if (ref.watch(logLevelProvider
|
|
.select((level) => level.value <= Level.CONFIG.value))) {
|
|
return const Align(
|
|
alignment: Alignment.bottomCenter,
|
|
child: IgnorePointer(
|
|
child: Text(
|
|
'WARNING: Potentially sensitive data is being logged!',
|
|
textDirection: TextDirection.ltr,
|
|
style: TextStyle(
|
|
color: Colors.red,
|
|
fontWeight: FontWeight.bold,
|
|
),
|
|
),
|
|
),
|
|
);
|
|
}
|
|
return const SizedBox();
|
|
}),
|
|
],
|
|
);
|
|
}
|
|
}
|