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

library sky_tools.device;

import 'dart:async';
import 'dart:io';
import 'dart:math';

import 'package:logging/logging.dart';
import 'package:path/path.dart' as path;

import 'application_package.dart';
import 'process.dart';

final Logger _logging = new Logger('sky_tools.device');

abstract class _Device {
  final String id;
  static Map<String, _Device> _deviceCache = {};

  factory _Device(String className, [String id = null]) {
    if (id == null) {
      if (className == AndroidDevice.className) {
        id = AndroidDevice.defaultDeviceID;
      } else if (className == IOSDevice.className) {
        id = IOSDevice.defaultDeviceID;
      } else {
        throw 'Attempted to create a Device of unknown type $className';
      }
    }

    return _deviceCache.putIfAbsent(id, () {
      if (className == AndroidDevice.className) {
        final device = new AndroidDevice._(id);
        _deviceCache[id] = device;
        return device;
      } else if (className == IOSDevice.className) {
        final device = new IOSDevice._(id);
        _deviceCache[id] = device;
        return device;
      } else {
        throw 'Attempted to create a Device of unknown type $className';
      }
    });
  }

  _Device._(this.id);

  /// Install an app package on the current device
  bool installApp(ApplicationPackage app);

  /// Check if the device is currently connected
  bool isConnected();

  /// Check if the current version of the given app is already installed
  bool isAppInstalled(ApplicationPackage app);

  /// Start an app package on the current device
  Future<bool> startApp(ApplicationPackage app);

  /// Stop an app package on the current device
  Future<bool> stopApp(ApplicationPackage app);
}

class IOSDevice extends _Device {
  static const String className = 'IOSDevice';
  static final String defaultDeviceID = 'default_ios_id';

  static const String _macInstructions =
      'To work with iOS devices, please install ideviceinstaller. '
      'If you use homebrew, you can install it with '
      '"\$ brew install ideviceinstaller".';
  static const String _linuxInstructions =
      'To work with iOS devices, please install ideviceinstaller. '
      'On Ubuntu or Debian, you can install it with '
      '"\$ apt-get install ideviceinstaller".';

  String _installerPath;
  String get installerPath => _installerPath;

  String _listerPath;
  String get listerPath => _listerPath;

  String _informerPath;
  String get informerPath => _informerPath;

  String _debuggerPath;
  String get debuggerPath => _debuggerPath;

  String _name;
  String get name => _name;

  factory IOSDevice({String id, String name}) {
    IOSDevice device = new _Device(className, id);
    device._name = name;
    return device;
  }

  IOSDevice._(String id) : super._(id) {
    _installerPath = _checkForCommand('ideviceinstaller');
    _listerPath = _checkForCommand('idevice_id');
    _informerPath = _checkForCommand('ideviceinfo');
    _debuggerPath = _checkForCommand('idevicedebug');
  }

  static List<IOSDevice> getAttachedDevices([IOSDevice mockIOS]) {
    List<IOSDevice> devices = [];
    for (String id in _getAttachedDeviceIDs(mockIOS)) {
      String name = _getDeviceName(id, mockIOS);
      devices.add(new IOSDevice(id: id, name: name));
    }
    return devices;
  }

  static List<String> _getAttachedDeviceIDs([IOSDevice mockIOS]) {
    String listerPath =
        (mockIOS != null) ? mockIOS.listerPath : _checkForCommand('idevice_id');
    return runSync([listerPath, '-l']).trim().split('\n');
  }

  static String _getDeviceName(String deviceID, [IOSDevice mockIOS]) {
    String informerPath = (mockIOS != null)
        ? mockIOS.informerPath
        : _checkForCommand('ideviceinfo');
    return runSync([informerPath, '-k', 'DeviceName', '-u', deviceID]);
  }

  static final Map<String, String> _commandMap = {};
  static String _checkForCommand(String command,
      [String macInstructions = _macInstructions,
      String linuxInstructions = _linuxInstructions]) {
    return _commandMap.putIfAbsent(command, () {
      try {
        command = runCheckedSync(['which', command]).trim();
      } catch (e) {
        if (Platform.isMacOS) {
          _logging.severe(macInstructions);
        } else if (Platform.isLinux) {
          _logging.severe(linuxInstructions);
        } else {
          _logging.severe('$command is not available on your platform.');
        }
      }
      return command;
    });
  }

  @override
  bool installApp(ApplicationPackage app) {
    if (id == defaultDeviceID) {
      runCheckedSync([installerPath, '-i', app.appPath]);
    } else {
      runCheckedSync([installerPath, '-u', id, '-i', app.appPath]);
    }
    return false;
  }

  @override
  bool isConnected() {
    List<String> ids = _getAttachedDeviceIDs();
    for (String id in ids) {
      if (id == this.id || this.id == defaultDeviceID) {
        return true;
      }
    }
    return false;
  }

  @override
  bool isAppInstalled(ApplicationPackage app) {
    try {
      String apps = runCheckedSync([installerPath, '-l']);
      if (new RegExp(app.appPackageID, multiLine: true).hasMatch(apps)) {
        return true;
      }
    } catch (e) {
      return false;
    }
    return false;
  }

  @override
  Future<bool> startApp(ApplicationPackage app) async {
    if (!isAppInstalled(app)) {
      return false;
    }
    // idevicedebug hangs forever after launching the app, so kill it after
    // giving it plenty of time to send the launch command.
    return runAndKill(
        [debuggerPath, 'run', app.appPackageID], new Duration(seconds: 3)).then(
        (_) {
      return true;
    }, onError: (e) {
      _logging.info('Failure running $debuggerPath: ', e);
      return false;
    });
  }

  @override
  Future<bool> stopApp(ApplicationPackage app) async {
    // Currently we don't have a way to stop an app running on iOS.
    return false;
  }
}

class AndroidDevice extends _Device {
  static const String _ADB_PATH = 'adb';
  static const String _observatoryPort = '8181';
  static const String _serverPort = '9888';

  static const String className = 'AndroidDevice';
  static final String defaultDeviceID = 'default_android_device';

  String productID;
  String modelID;
  String deviceCodeName;

  String _adbPath;
  String get adbPath => _adbPath;
  bool _hasAdb = false;
  bool _hasValidAndroid = false;

  factory AndroidDevice(
      {String id: null,
      String productID: null,
      String modelID: null,
      String deviceCodeName: null}) {
    AndroidDevice device = new _Device(className, id);
    device.productID = productID;
    device.modelID = modelID;
    device.deviceCodeName = deviceCodeName;
    return device;
  }

  /// mockAndroid argument is only to facilitate testing with mocks, so that
  /// we don't have to rely on the test setup having adb available to it.
  static List<AndroidDevice> getAttachedDevices([AndroidDevice mockAndroid]) {
    List<AndroidDevice> devices = [];
    String adbPath =
        (mockAndroid != null) ? mockAndroid.adbPath : _getAdbPath();
    List<String> output =
        runSync([adbPath, 'devices', '-l']).trim().split('\n');
    RegExp deviceInfo = new RegExp(
        r'^(\S+)\s+device\s+\S+\s+product:(\S+)\s+model:(\S+)\s+device:(\S+)$');
    // Skip first line, which is always 'List of devices attached'.
    for (String line in output.skip(1)) {
      Match match = deviceInfo.firstMatch(line);
      if (match != null) {
        String deviceID = match[1];
        String productID = match[2];
        String modelID = match[3];
        String deviceCodeName = match[4];

        devices.add(new AndroidDevice(
            id: deviceID,
            productID: productID,
            modelID: modelID,
            deviceCodeName: deviceCodeName));
      } else {
        _logging.warning('Unexpected failure parsing device information '
            'from adb output:\n$line\n'
            'Please report a bug at http://flutter.io/');
      }
    }
    return devices;
  }

  AndroidDevice._(id) : super._(id) {
    _adbPath = _getAdbPath();
    _hasAdb = _checkForAdb();

    // Checking for lollipop only needs to be done if we are starting an
    // app, but it has an important side effect, which is to discard any
    // progress messages if the adb server is restarted.
    _hasValidAndroid = _checkForLollipopOrLater();

    if (!_hasAdb || !_hasValidAndroid) {
      _logging.severe('Unable to run on Android.');
    }
  }

  static String _getAdbPath() {
    if (Platform.environment.containsKey('ANDROID_HOME')) {
      String androidHomeDir = Platform.environment['ANDROID_HOME'];
      String adbPath1 =
          path.join(androidHomeDir, 'sdk', 'platform-tools', 'adb');
      String adbPath2 = path.join(androidHomeDir, 'platform-tools', 'adb');
      if (FileSystemEntity.isFileSync(adbPath1)) {
        return adbPath1;
      } else if (FileSystemEntity.isFileSync(adbPath2)) {
        return adbPath2;
      } else {
        _logging.info('"adb" not found at\n  "$adbPath1" or\n  "$adbPath2"\n' +
            'using default path "$_ADB_PATH"');
        return _ADB_PATH;
      }
    } else {
      return _ADB_PATH;
    }
  }

  bool _isValidAdbVersion(String adbVersion) {
    // Sample output: 'Android Debug Bridge version 1.0.31'
    Match versionFields =
        new RegExp(r'(\d+)\.(\d+)\.(\d+)').firstMatch(adbVersion);
    if (versionFields != null) {
      int majorVersion = int.parse(versionFields[1]);
      int minorVersion = int.parse(versionFields[2]);
      int patchVersion = int.parse(versionFields[3]);
      if (majorVersion > 1) {
        return true;
      }
      if (majorVersion == 1 && minorVersion > 0) {
        return true;
      }
      if (majorVersion == 1 && minorVersion == 0 && patchVersion >= 32) {
        return true;
      }
      return false;
    }
    _logging.warning(
        'Unrecognized adb version string $adbVersion. Skipping version check.');
    return true;
  }

  bool _checkForAdb() {
    try {
      String adbVersion = runCheckedSync([adbPath, 'version']);
      if (_isValidAdbVersion(adbVersion)) {
        return true;
      }

      String locatedAdbPath = runCheckedSync(['which', 'adb']);
      _logging.severe('"$locatedAdbPath" is too old. '
          'Please install version 1.0.32 or later.\n'
          'Try setting ANDROID_HOME to the path to your Android SDK install. '
          'Android builds are unavailable.');
    } catch (e, stack) {
      _logging.severe('"adb" not found in \$PATH. '
          'Please install the Android SDK or set ANDROID_HOME '
          'to the path of your Android SDK install.');
      _logging.info(e);
      _logging.info(stack);
    }
    return false;
  }

  bool _checkForLollipopOrLater() {
    try {
      // If the server is automatically restarted, then we get irrelevant
      // output lines like this, which we want to ignore:
      //   adb server is out of date.  killing..
      //   * daemon started successfully *
      runCheckedSync([adbPath, 'start-server']);

      // Sample output: '22'
      String sdkVersion =
          runCheckedSync([adbPath, 'shell', 'getprop', 'ro.build.version.sdk'])
              .trimRight();

      int sdkVersionParsed =
          int.parse(sdkVersion, onError: (String source) => null);
      if (sdkVersionParsed == null) {
        _logging.severe('Unexpected response from getprop: "$sdkVersion"');
        return false;
      }
      if (sdkVersionParsed < 22) {
        _logging.severe('Version "$sdkVersion" of the Android SDK is too old. '
            'Please install Lollipop (version 22) or later.');
        return false;
      }
      return true;
    } catch (e, stack) {
      _logging.severe('Unexpected failure from adb: ', e, stack);
    }
    return false;
  }

  String _getDeviceSha1Path(ApplicationPackage app) {
    return '/sdcard/${app.appPackageID}/${app.appFileName}.sha1';
  }

  String _getDeviceApkSha1(ApplicationPackage app) {
    return runCheckedSync([adbPath, 'shell', 'cat', _getDeviceSha1Path(app)]);
  }

  String _getSourceSha1(ApplicationPackage app) {
    String sha1 =
        runCheckedSync(['shasum', '-a', '1', '-p', app.appPath]).split(' ')[0];
    return sha1;
  }

  @override
  bool isAppInstalled(ApplicationPackage app) {
    if (!isConnected()) {
      return false;
    }
    if (runCheckedSync([adbPath, 'shell', 'pm', 'path', app.appPackageID]) ==
        '') {
      _logging.info(
          'TODO(iansf): move this log to the caller. ${app.appFileName} is not on the device. Installing now...');
      return false;
    }
    if (_getDeviceApkSha1(app) != _getSourceSha1(app)) {
      _logging.info(
          'TODO(iansf): move this log to the caller. ${app.appFileName} is out of date. Installing now...');
      return false;
    }
    return true;
  }

  @override
  bool installApp(ApplicationPackage app) {
    if (!isConnected()) {
      _logging.info('Android device not connected. Not installing.');
      return false;
    }
    if (!FileSystemEntity.isFileSync(app.appPath)) {
      _logging.severe('"${app.appPath}" does not exist.');
      return false;
    }

    runCheckedSync([adbPath, 'install', '-r', app.appPath]);

    Directory tempDir = Directory.systemTemp;
    String sha1Path = path.join(
        tempDir.path, (app.appPath + '.sha1').replaceAll(path.separator, '_'));
    File sha1TempFile = new File(sha1Path);
    sha1TempFile.writeAsStringSync(_getSourceSha1(app), flush: true);
    runCheckedSync([adbPath, 'push', sha1Path, _getDeviceSha1Path(app)]);
    sha1TempFile.deleteSync();
    return true;
  }

  Future<bool> startServer(
      String target, bool poke, bool checked, AndroidApk apk) async {
    String serverRoot = '';
    String mainDart = '';
    String missingMessage = '';
    if (await FileSystemEntity.isDirectory(target)) {
      serverRoot = target;
      mainDart = path.join(serverRoot, 'lib', 'main.dart');
      missingMessage = 'Missing lib/main.dart in project: $serverRoot';
    } else {
      serverRoot = Directory.current.path;
      mainDart = target;
      missingMessage = '$mainDart does not exist.';
    }

    if (!await FileSystemEntity.isFile(mainDart)) {
      _logging.severe(missingMessage);
      return false;
    }

    if (!poke) {
      // Set up port forwarding for observatory.
      String observatoryPortString = 'tcp:$_observatoryPort';
      runCheckedSync(
          [adbPath, 'forward', observatoryPortString, observatoryPortString]);

      // Actually start the server.
      await Process.start('pub', ['run', 'sky_tools:sky_server', _serverPort],
          workingDirectory: serverRoot, mode: ProcessStartMode.DETACHED);

      // Set up reverse port-forwarding so that the Android app can reach the
      // server running on localhost.
      String serverPortString = 'tcp:$_serverPort';
      runCheckedSync([adbPath, 'reverse', serverPortString, serverPortString]);
    }

    String relativeDartMain = path.relative(mainDart, from: serverRoot);
    String url = 'http://localhost:$_serverPort/$relativeDartMain';
    if (poke) {
      url += '?rand=${new Random().nextDouble()}';
    }

    // Actually launch the app on Android.
    List<String> cmd = [
      adbPath,
      'shell',
      'am',
      'start',
      '-a',
      'android.intent.action.VIEW',
      '-d',
      url,
    ];
    if (checked) {
      cmd.addAll(['--ez', 'enable-checked-mode', 'true']);
    }
    cmd.add(apk.component);

    runCheckedSync(cmd);

    return true;
  }

  @override
  Future<bool> startApp(AndroidApk apk) async {
    // Android currently has to be started with startServer(...).
    assert(false);
    return false;
  }

  Future<bool> stopApp(AndroidApk apk) async {
    // Turn off reverse port forwarding
    runSync([adbPath, 'reverse', '--remove', 'tcp:$_serverPort']);
    // Stop the app
    runSync([adbPath, 'shell', 'am', 'force-stop', apk.appPackageID]);
    // Kill the server
    if (Platform.isMacOS) {
      String pid = runSync(['lsof', '-i', ':$_serverPort', '-t']);
      // Killing a pid with a shell command from within dart is hard,
      // so use a library command, but it's still nice to give the
      // equivalent command when doing verbose logging.
      _logging.info('kill $pid');
      Process.killPid(int.parse(pid));
    } else {
      runSync(['fuser', '-k', '$_serverPort/tcp']);
    }

    return true;
  }

  void clearLogs() {
    runSync([adbPath, 'logcat', '-c']);
  }

  Future<int> logs({bool clear: false}) {
    if (clear) {
      clearLogs();
    }

    return runCommandAndStreamOutput([
      adbPath,
      'logcat',
      '-v',
      'tag', // Only log the tag and the message
      '-s',
      'sky',
      'chromium',
    ], prefix: 'ANDROID: ');
  }

  void startTracing(AndroidApk apk) {
    runCheckedSync([
      adbPath,
      'shell',
      'am',
      'broadcast',
      '-a',
      '${apk.appPackageID}.TRACING_START'
    ]);
  }

  String stopTracing(AndroidApk apk) {
    clearLogs();
    runCheckedSync([
      adbPath,
      'shell',
      'am',
      'broadcast',
      '-a',
      '${apk.appPackageID}.TRACING_STOP'
    ]);

    RegExp traceRegExp = new RegExp(r'Saving trace to (\S+)', multiLine: true);
    RegExp completeRegExp = new RegExp(r'Trace complete', multiLine: true);

    String tracePath = null;
    bool isComplete = false;
    while (!isComplete) {
      String logs = runSync([adbPath, 'logcat', '-d']);
      Match fileMatch = traceRegExp.firstMatch(logs);
      if (fileMatch[1] != null) {
        tracePath = fileMatch[1];
      }
      isComplete = completeRegExp.hasMatch(logs);
    }

    if (tracePath != null) {
      // adb root exits with 0 even if the command fails,
      // so check the output string
      String output = runSync([adbPath, 'root']);
      if (new RegExp(r'.*cannot run as root.*').hasMatch(output)) {
        _logging
            .severe('Unable to download trace "${path.basename(tracePath)}"\n'
                'You need to be able to run adb as root '
                'on your android device');
        return null;
      }
      runSync([adbPath, 'pull', tracePath]);
      runSync([adbPath, 'shell', 'rm', tracePath]);
      return path.basename(tracePath);
    }
    _logging.warning('No trace file detected. '
        'Did you remember to start the trace before stopping it?');
    return null;
  }

  @override
  bool isConnected() => _hasValidAndroid;
}
