// Copyright 2014 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

import 'package:meta/meta.dart';

import '../base/platform.dart';
import '../build_info.dart';

/// Quiver has this, but unfortunately we can't depend on it bc flutter_tools
/// uses non-nullsafe quiver by default (because of dwds).
bool _listsEqual(List<dynamic>? a, List<dynamic>? b) {
  if (a == b) {
    return true;
  }
  if (a == null || b == null) {
    return false;
  }
  if (a.length != b.length) {
    return false;
  }

  return a.asMap().entries.every((MapEntry<int, dynamic> e) => e.value == b[e.key]);
}

/// The normal [RegExp.==] operator is inherited from [Object], so only
/// returns true when the regexes are the same instance.
///
/// This function instead _should_ return true when the regexes are
/// functionally the same, i.e. when they have the same matches & captures for
/// any given input. At least that's the goal, in reality this has lots of false
/// negatives (for example when the flags differ). Still better than [RegExp.==].
bool _regexesEqual(RegExp? a, RegExp? b) {
  if (a == b) {
    return true;
  }
  if (a == null || b == null) {
    return false;
  }

  return a.pattern == b.pattern
    && a.isMultiLine == b.isMultiLine
    && a.isCaseSensitive == b.isCaseSensitive
    && a.isUnicode == b.isUnicode
    && a.isDotAll == b.isDotAll;
}

/// Something went wrong while trying to load the custom devices config from the
/// JSON representation. Maybe some value is missing, maybe something has the
/// wrong type, etc.
@immutable
class CustomDeviceRevivalException implements Exception {
  const CustomDeviceRevivalException(this.message);

  const CustomDeviceRevivalException.fromDescriptions(
    String fieldDescription,
    String expectedValueDescription
  ) : message = 'Expected $fieldDescription to be $expectedValueDescription.';

  final String message;

  @override
  String toString() {
    return message;
  }

  @override
  bool operator ==(Object other) {
    return (other is CustomDeviceRevivalException) &&
        (other.message == message);
  }

  @override
  int get hashCode => message.hashCode;
}

/// A single configured custom device.
///
/// In the custom devices config file on disk, there may be multiple custom
/// devices configured.
@immutable
class CustomDeviceConfig {
  const CustomDeviceConfig({
    required this.id,
    required this.label,
    required this.sdkNameAndVersion,
    this.platform,
    required this.enabled,
    required this.pingCommand,
    this.pingSuccessRegex,
    required this.postBuildCommand,
    required this.installCommand,
    required this.uninstallCommand,
    required this.runDebugCommand,
    this.forwardPortCommand,
    this.forwardPortSuccessRegex,
    this.screenshotCommand
  }) : assert(forwardPortCommand == null || forwardPortSuccessRegex != null),
       assert(
         platform == null
         || platform == TargetPlatform.linux_x64
         || platform == TargetPlatform.linux_arm64
       );

  /// Create a CustomDeviceConfig from some JSON value.
  /// If anything fails internally (some value doesn't have the right type,
  /// some value is missing, etc) a [CustomDeviceRevivalException] with the description
  /// of the error is thrown. (No exceptions/errors other than JsonRevivalException
  /// should ever be thrown by this factory.)
  factory CustomDeviceConfig.fromJson(dynamic json) {
    final Map<String, dynamic> typedMap = _castJsonObject(
      json,
      'device configuration',
      'a JSON object'
    );

    final List<String>? forwardPortCommand = _castStringListOrNull(
      typedMap[_kForwardPortCommand],
      _kForwardPortCommand,
      'null or array of strings with at least one element',
      minLength: 1
    );

    final RegExp? forwardPortSuccessRegex = _convertToRegexOrNull(
      typedMap[_kForwardPortSuccessRegex],
      _kForwardPortSuccessRegex,
      'null or string-ified regex'
    );

    final String? archString = _castStringOrNull(
      typedMap[_kPlatform],
      _kPlatform,
      'null or one of linux-arm64, linux-x64'
    );

    late TargetPlatform? platform;
    try {
      platform = archString == null
        ? null
        : getTargetPlatformForName(archString);
    } on FallThroughError {
      throw const CustomDeviceRevivalException.fromDescriptions(
        _kPlatform,
        'null or one of linux-arm64, linux-x64'
      );
    }

    if (platform != null
        && platform != TargetPlatform.linux_arm64
        && platform != TargetPlatform.linux_x64
    ) {
      throw const CustomDeviceRevivalException.fromDescriptions(
        _kPlatform,
        'null or one of linux-arm64, linux-x64'
      );
    }

    if (forwardPortCommand != null && forwardPortSuccessRegex == null) {
      throw const CustomDeviceRevivalException('When forwardPort is given, forwardPortSuccessRegex must be specified too.');
    }

    return CustomDeviceConfig(
      id: _castString(typedMap[_kId], _kId, 'a string'),
      label: _castString(typedMap[_kLabel], _kLabel, 'a string'),
      sdkNameAndVersion: _castString(typedMap[_kSdkNameAndVersion], _kSdkNameAndVersion, 'a string'),
      platform: platform,
      enabled: _castBool(typedMap[_kEnabled], _kEnabled, 'a boolean'),
      pingCommand: _castStringList(
        typedMap[_kPingCommand],
        _kPingCommand,
        'array of strings with at least one element',
        minLength: 1
      ),
      pingSuccessRegex: _convertToRegexOrNull(typedMap[_kPingSuccessRegex], _kPingSuccessRegex, 'null or string-ified regex'),
      postBuildCommand: _castStringListOrNull(
        typedMap[_kPostBuildCommand],
        _kPostBuildCommand,
        'null or array of strings with at least one element',
        minLength: 1,
      ),
      installCommand: _castStringList(
        typedMap[_kInstallCommand],
        _kInstallCommand,
        'array of strings with at least one element',
        minLength: 1
      ),
      uninstallCommand: _castStringList(
        typedMap[_kUninstallCommand],
        _kUninstallCommand,
        'array of strings with at least one element',
        minLength: 1
      ),
      runDebugCommand: _castStringList(
        typedMap[_kRunDebugCommand],
        _kRunDebugCommand,
        'array of strings with at least one element',
        minLength: 1
      ),
      forwardPortCommand: forwardPortCommand,
      forwardPortSuccessRegex: forwardPortSuccessRegex,
      screenshotCommand: _castStringListOrNull(
        typedMap[_kScreenshotCommand],
        _kScreenshotCommand,
        'array of strings with at least one element',
        minLength: 1
      )
    );
  }

  static const String _kId = 'id';
  static const String _kLabel = 'label';
  static const String _kSdkNameAndVersion = 'sdkNameAndVersion';
  static const String _kPlatform = 'platform';
  static const String _kEnabled = 'enabled';
  static const String _kPingCommand = 'ping';
  static const String _kPingSuccessRegex = 'pingSuccessRegex';
  static const String _kPostBuildCommand = 'postBuild';
  static const String _kInstallCommand = 'install';
  static const String _kUninstallCommand = 'uninstall';
  static const String _kRunDebugCommand = 'runDebug';
  static const String _kForwardPortCommand = 'forwardPort';
  static const String _kForwardPortSuccessRegex = 'forwardPortSuccessRegex';
  static const String _kScreenshotCommand = 'screenshot';

  /// An example device config used for creating the default config file.
  /// Uses windows-specific ping and pingSuccessRegex. For the linux and macOs
  /// example config, see [exampleUnix].
  static final CustomDeviceConfig exampleWindows = CustomDeviceConfig(
    id: 'pi',
    label: 'Raspberry Pi',
    sdkNameAndVersion: 'Raspberry Pi 4 Model B+',
    platform: TargetPlatform.linux_arm64,
    enabled: false,
    pingCommand: const <String>[
      'ping',
      '-w', '500',
      '-n', '1',
      'raspberrypi',
    ],
    pingSuccessRegex: RegExp(r'[<=]\d+ms'),
    postBuildCommand: null,
    installCommand: const <String>[
      'scp',
      '-r',
      '-o', 'BatchMode=yes',
      r'${localPath}',
      r'pi@raspberrypi:/tmp/${appName}',
    ],
    uninstallCommand: const <String>[
      'ssh',
      '-o', 'BatchMode=yes',
      'pi@raspberrypi',
      r'rm -rf "/tmp/${appName}"',
    ],
    runDebugCommand: const <String>[
      'ssh',
      '-o', 'BatchMode=yes',
      'pi@raspberrypi',
      r'flutter-pi "/tmp/${appName}"',
    ],
    forwardPortCommand: const <String>[
      'ssh',
      '-o', 'BatchMode=yes',
      '-o', 'ExitOnForwardFailure=yes',
      '-L', r'127.0.0.1:${hostPort}:127.0.0.1:${devicePort}',
      'pi@raspberrypi',
    ],
    forwardPortSuccessRegex: RegExp('Linux'),
    screenshotCommand: const <String>[
      'ssh',
      '-o', 'BatchMode=yes',
      'pi@raspberrypi',
      r"fbgrab /tmp/screenshot.png && cat /tmp/screenshot.png | base64 | tr -d ' \n\t'",
    ],
  );

  /// An example device config used for creating the default config file.
  /// Uses ping and pingSuccessRegex values that only work on linux or macOs.
  /// For the Windows example config, see [exampleWindows].
  static final CustomDeviceConfig exampleUnix = exampleWindows.copyWith(
    pingCommand: const <String>[
      'ping',
      '-w', '1',
      '-c', '1',
      'raspberrypi'
    ],
    explicitPingSuccessRegex: true,
    pingSuccessRegex: null
  );

  /// Returns an example custom device config that works on the given host platform.
  ///
  /// This is not the platform of the target device, it's the platform of the
  /// development machine. Examples for different platforms may be different
  /// because for example the ping command is different on Windows or Linux/macOS.
  static CustomDeviceConfig getExampleForPlatform(Platform platform) {
    if (platform.isWindows) {
      return exampleWindows;
    }
    if (platform.isLinux || platform.isMacOS) {
      return exampleUnix;
    }
    throw FallThroughError();
  }

  final String id;
  final String label;
  final String sdkNameAndVersion;
  final TargetPlatform? platform;
  final bool enabled;
  final List<String> pingCommand;
  final RegExp? pingSuccessRegex;
  final List<String>? postBuildCommand;
  final List<String> installCommand;
  final List<String> uninstallCommand;
  final List<String> runDebugCommand;
  final List<String>? forwardPortCommand;
  final RegExp? forwardPortSuccessRegex;
  final List<String>? screenshotCommand;

  /// Returns true when this custom device config uses port forwarding,
  /// which is the case when [forwardPortCommand] is not null.
  bool get usesPortForwarding => forwardPortCommand != null;

  /// Returns true when this custom device config supports screenshotting,
  /// which is the case when the [screenshotCommand] is not null.
  bool get supportsScreenshotting => screenshotCommand != null;

  /// Invokes and returns the result of [closure].
  ///
  /// If anything at all is thrown when executing the closure, a
  /// [CustomDeviceRevivalException] is thrown with the given [fieldDescription] and
  /// [expectedValueDescription].
  static T _maybeRethrowAsRevivalException<T>(T Function() closure, String fieldDescription, String expectedValueDescription) {
    try {
      return closure();
    } on Object {
      throw CustomDeviceRevivalException.fromDescriptions(fieldDescription, expectedValueDescription);
    }
  }

  /// Tries to make a string-keyed, non-null map from [value].
  ///
  /// If the value is null or not a valid string-keyed map, a [CustomDeviceRevivalException]
  /// with the given [fieldDescription] and [expectedValueDescription] is thrown.
  static Map<String, dynamic> _castJsonObject(dynamic value, String fieldDescription, String expectedValueDescription) {
    if (value == null) {
      throw CustomDeviceRevivalException.fromDescriptions(fieldDescription, expectedValueDescription);
    }

    return _maybeRethrowAsRevivalException(
      () => Map<String, dynamic>.from(value as Map<dynamic, dynamic>),
      fieldDescription,
      expectedValueDescription,
    );
  }

  /// Tries to cast [value] to a bool.
  ///
  /// If the value is null or not a bool, a [CustomDeviceRevivalException] with the given
  /// [fieldDescription] and [expectedValueDescription] is thrown.
  static bool _castBool(dynamic value, String fieldDescription, String expectedValueDescription) {
    if (value == null) {
      throw CustomDeviceRevivalException.fromDescriptions(fieldDescription, expectedValueDescription);
    }

    return _maybeRethrowAsRevivalException(
      () => value as bool,
      fieldDescription,
      expectedValueDescription,
    );
  }

  /// Tries to cast [value] to a String.
  ///
  /// If the value is null or not a String, a [CustomDeviceRevivalException] with the given
  /// [fieldDescription] and [expectedValueDescription] is thrown.
  static String _castString(dynamic value, String fieldDescription, String expectedValueDescription) {
    if (value == null) {
      throw CustomDeviceRevivalException.fromDescriptions(fieldDescription, expectedValueDescription);
    }

    return _maybeRethrowAsRevivalException(
      () => value as String,
      fieldDescription,
      expectedValueDescription,
    );
  }

  /// Tries to cast [value] to a nullable String.
  ///
  /// If the value not null and not a String, a [CustomDeviceRevivalException] with the given
  /// [fieldDescription] and [expectedValueDescription] is thrown.
  static String? _castStringOrNull(dynamic value, String fieldDescription, String expectedValueDescription) {
    if (value == null) {
      return null;
    }

    return _castString(value, fieldDescription, expectedValueDescription);
  }

  /// Tries to make a list of strings from [value].
  ///
  /// If the value is null or not a list containing only string values,
  /// a [CustomDeviceRevivalException] with the given [fieldDescription] and
  /// [expectedValueDescription] is thrown.
  static List<String> _castStringList(
    dynamic value,
    String fieldDescription,
    String expectedValueDescription, {
    int minLength = 0,
  }) {
    if (value == null) {
      throw CustomDeviceRevivalException.fromDescriptions(fieldDescription, expectedValueDescription);
    }

    final List<String> list = _maybeRethrowAsRevivalException(
      () => List<String>.from(value as Iterable<dynamic>),
      fieldDescription,
      expectedValueDescription,
    );

    if (list.length < minLength) {
      throw CustomDeviceRevivalException.fromDescriptions(fieldDescription, expectedValueDescription);
    }

    return list;
  }

  /// Tries to make a list of strings from [value], or returns null if [value]
  /// is null.
  ///
  /// If the value is not null and not a list containing only string values,
  /// a [CustomDeviceRevivalException] with the given [fieldDescription] and
  /// [expectedValueDescription] is thrown.
  static List<String>? _castStringListOrNull(
    dynamic value,
    String fieldDescription,
    String expectedValueDescription, {
    int minLength = 0,
  }) {
    if (value == null) {
      return null;
    }

    return _castStringList(value, fieldDescription, expectedValueDescription, minLength: minLength);
  }

  /// Tries to construct a RegExp from [value], or returns null if [value]
  /// is null.
  ///
  /// If the value is not null and not a valid string-ified regex,
  /// a [CustomDeviceRevivalException] with the given [fieldDescription] and
  /// [expectedValueDescription] is thrown.
  static RegExp? _convertToRegexOrNull(dynamic value, String fieldDescription, String expectedValueDescription) {
    if (value == null) {
      return null;
    }

    return _maybeRethrowAsRevivalException(
      () => RegExp(value as String),
      fieldDescription,
      expectedValueDescription,
    );
  }

  Object toJson() {
    return <String, Object?>{
      _kId: id,
      _kLabel: label,
      _kSdkNameAndVersion: sdkNameAndVersion,
      _kPlatform: platform == null ? null : getNameForTargetPlatform(platform!),
      _kEnabled: enabled,
      _kPingCommand: pingCommand,
      _kPingSuccessRegex: pingSuccessRegex?.pattern,
      _kPostBuildCommand: postBuildCommand,
      _kInstallCommand: installCommand,
      _kUninstallCommand: uninstallCommand,
      _kRunDebugCommand: runDebugCommand,
      _kForwardPortCommand: forwardPortCommand,
      _kForwardPortSuccessRegex: forwardPortSuccessRegex?.pattern,
      _kScreenshotCommand: screenshotCommand,
    };
  }

  CustomDeviceConfig copyWith({
    String? id,
    String? label,
    String? sdkNameAndVersion,
    bool explicitPlatform = false,
    TargetPlatform? platform,
    bool? enabled,
    List<String>? pingCommand,
    bool explicitPingSuccessRegex = false,
    RegExp? pingSuccessRegex,
    bool explicitPostBuildCommand = false,
    List<String>? postBuildCommand,
    List<String>? installCommand,
    List<String>? uninstallCommand,
    List<String>? runDebugCommand,
    bool explicitForwardPortCommand = false,
    List<String>? forwardPortCommand,
    bool explicitForwardPortSuccessRegex = false,
    RegExp? forwardPortSuccessRegex,
    bool explicitScreenshotCommand = false,
    List<String>? screenshotCommand
  }) {
    return CustomDeviceConfig(
      id: id ?? this.id,
      label: label ?? this.label,
      sdkNameAndVersion: sdkNameAndVersion ?? this.sdkNameAndVersion,
      platform: explicitPlatform ? platform : (platform ?? this.platform),
      enabled: enabled ?? this.enabled,
      pingCommand: pingCommand ?? this.pingCommand,
      pingSuccessRegex: explicitPingSuccessRegex ? pingSuccessRegex : (pingSuccessRegex ?? this.pingSuccessRegex),
      postBuildCommand: explicitPostBuildCommand ? postBuildCommand : (postBuildCommand ?? this.postBuildCommand),
      installCommand: installCommand ?? this.installCommand,
      uninstallCommand: uninstallCommand ?? this.uninstallCommand,
      runDebugCommand: runDebugCommand ?? this.runDebugCommand,
      forwardPortCommand: explicitForwardPortCommand ? forwardPortCommand : (forwardPortCommand ?? this.forwardPortCommand),
      forwardPortSuccessRegex: explicitForwardPortSuccessRegex ? forwardPortSuccessRegex : (forwardPortSuccessRegex ?? this.forwardPortSuccessRegex),
      screenshotCommand: explicitScreenshotCommand ? screenshotCommand : (screenshotCommand ?? this.screenshotCommand),
    );
  }

  @override
  bool operator ==(Object other) {
    return other is CustomDeviceConfig
      && other.id == id
      && other.label == label
      && other.sdkNameAndVersion == sdkNameAndVersion
      && other.platform == platform
      && other.enabled == enabled
      && _listsEqual(other.pingCommand, pingCommand)
      && _regexesEqual(other.pingSuccessRegex, pingSuccessRegex)
      && _listsEqual(other.postBuildCommand, postBuildCommand)
      && _listsEqual(other.installCommand, installCommand)
      && _listsEqual(other.uninstallCommand, uninstallCommand)
      && _listsEqual(other.runDebugCommand, runDebugCommand)
      && _listsEqual(other.forwardPortCommand, forwardPortCommand)
      && _regexesEqual(other.forwardPortSuccessRegex, forwardPortSuccessRegex)
      && _listsEqual(other.screenshotCommand, screenshotCommand);
  }

  @override
  int get hashCode {
    return id.hashCode
      ^ label.hashCode
      ^ sdkNameAndVersion.hashCode
      ^ platform.hashCode
      ^ enabled.hashCode
      ^ pingCommand.hashCode
      ^ (pingSuccessRegex?.pattern).hashCode
      ^ postBuildCommand.hashCode
      ^ installCommand.hashCode
      ^ uninstallCommand.hashCode
      ^ runDebugCommand.hashCode
      ^ forwardPortCommand.hashCode
      ^ (forwardPortSuccessRegex?.pattern).hashCode
      ^ screenshotCommand.hashCode;
  }

  @override
  String toString() {
    return 'CustomDeviceConfig('
      'id: $id, '
      'label: $label, '
      'sdkNameAndVersion: $sdkNameAndVersion, '
      'platform: $platform, '
      'enabled: $enabled, '
      'pingCommand: $pingCommand, '
      'pingSuccessRegex: $pingSuccessRegex, '
      'postBuildCommand: $postBuildCommand, '
      'installCommand: $installCommand, '
      'uninstallCommand: $uninstallCommand, '
      'runDebugCommand: $runDebugCommand, '
      'forwardPortCommand: $forwardPortCommand, '
      'forwardPortSuccessRegex: $forwardPortSuccessRegex, '
      'screenshotCommand: $screenshotCommand)';
  }
}
