// filepath: /Volumes/Data/Projects/Flutter/HMG_QLine/lib/services/crash_handler_service.dart
import 'dart:async';
import 'dart:developer';
import 'dart:ui';
import 'package:flutter/material.dart';
import 'package:hmg_qline/services/logger_service.dart';

// Abstract interface for crash handling (matches style of ConnectivityService)
abstract class CrashHandlerService {
  /// Install global error handlers for Flutter and platform errors.
  void setupGlobalErrorHandlers();

  /// Central crash handler for logging/reporting crashes.
  Future<void> handleCrash({required Object error, StackTrace? stackTrace, String? context});
}

class CrashHandlerServiceImp implements CrashHandlerService {
  final LoggerService loggerService;

  CrashHandlerServiceImp({required this.loggerService});

  /// Sets up global error handlers for Flutter framework errors and platform errors.
  @override
  void setupGlobalErrorHandlers() {
    // Flutter framework errors
    FlutterError.onError = (FlutterErrorDetails details) async {
      try {
        final error = details.exception;
        final stack = details.stack;
        await handleCrash(error: error, stackTrace: stack, context: 'FlutterError.onError');
      } catch (e, st) {
        // include stack trace in the log to avoid unused variable warning
        log('Error while handling FlutterError.onError: $e\nStack: $st');
        loggerService.logError('Error while handling FlutterError.onError: $e\nStack: $st');
      }
    };

    // PlatformDispatcher (engine) errors
    PlatformDispatcher.instance.onError = (Object error, StackTrace stack) {
      handleCrash(error: error, stackTrace: stack, context: 'PlatformDispatcher.onError');
      return true; // we handled it
    };

    // note: Zone errors are handled by runZonedGuarded where runApp is invoked
  }

  /// Central crash handler. Logs crash info and can be extended to report to remote services.
  @override
  Future<void> handleCrash({required Object error, StackTrace? stackTrace, String? context}) async {
    try {
      await loggerService.logCrash(error: error, stackTrace: stackTrace, context: context);
    } catch (e) {
      // ensure we don't throw while handling crashes
      log('CrashHandlerService failed to log crash: $e');
      loggerService.logError('CrashHandlerService failed to log crash: $e');
    }
  }
}
