import 'dart:async';

import 'package:connectivity_plus/connectivity_plus.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/services.dart';
import 'package:recording_tool/core/network/network_state.dart';

class NetworkMonitor {
  final _controller = StreamController<NetworkState>.broadcast();
  final _connectivity = Connectivity();

  StreamSubscription<List<ConnectivityResult>>? _subscription;
  NetworkState _state = const NetworkState(Reachability.unknown);

  Stream<NetworkState> get stream => _controller.stream;
  NetworkState get current => _state;

  void start() {
    try {
      _subscription = _connectivity.onConnectivityChanged.listen(
        (results) => _setOnline(_isOnline(results)),
        onError: (Object error, StackTrace stackTrace) {
          debugPrint('[NetworkMonitor] connectivity error: $error');
        },
      );

      _connectivity.checkConnectivity().then(
        (results) => _setOnline(_isOnline(results)),
        onError: (Object error, StackTrace stackTrace) {
          debugPrint('[NetworkMonitor] check error: $error');
        },
      );
    } on MissingPluginException catch (error) {
      debugPrint('[NetworkMonitor] plugin unavailable: $error');
    }
  }

  bool _isOnline(List<ConnectivityResult> results) {
    if (results.isEmpty) return false;
    if (results.contains(ConnectivityResult.none)) return false;
    return true;
  }

  void _setOnline(bool online) {
    final next = NetworkState(
      online ? Reachability.online : Reachability.offline,
    );
    if (next.reachability == _state.reachability) return;

    _state = next;
    _controller.add(_state);
  }

  void dispose() {
    _subscription?.cancel();
    _controller.close();
  }
}
