library pub.global_packages;
import 'dart:async';
import 'dart:io';
import 'package:path/path.dart' as p;
import 'package:barback/barback.dart';
import 'barback/asset_environment.dart';
import 'entrypoint.dart';
import 'executable.dart' as exe;
import 'io.dart';
import 'lock_file.dart';
import 'log.dart' as log;
import 'package.dart';
import 'pubspec.dart';
import 'sdk.dart' as sdk;
import 'solver/version_solver.dart';
import 'source/cached.dart';
import 'source/git.dart';
import 'source/path.dart';
import 'system_cache.dart';
import 'utils.dart';
import 'version.dart';
final _binStubPackagePattern = new RegExp(r"Package: ([a-zA-Z0-9_-]+)");
class GlobalPackages {
  final SystemCache cache;
  String get _directory => p.join(cache.rootDir, "global_packages");
  String get _binStubDir => p.join(cache.rootDir, "bin");
  GlobalPackages(this.cache);
  Future activateGit(String repo, List<String> executables,
      {bool overwriteBinStubs}) {
    final completer0 = new Completer();
    scheduleMicrotask(() {
      try {
        var source = cache.sources["git"] as GitSource;
        source.getPackageNameFromRepo(repo).then((x0) {
          try {
            var name = x0;
            _describeActive(name);
            _installInCache(
                new PackageDep(name, "git", VersionConstraint.any, repo),
                executables,
                overwriteBinStubs: overwriteBinStubs).then((x1) {
              try {
                x1;
                completer0.complete(null);
              } catch (e1) {
                completer0.completeError(e1);
              }
            }, onError: (e2) {
              completer0.completeError(e2);
            });
          } catch (e0) {
            completer0.completeError(e0);
          }
        }, onError: (e3) {
          completer0.completeError(e3);
        });
      } catch (e4) {
        completer0.completeError(e4);
      }
    });
    return completer0.future;
  }
  Future activateHosted(String name, VersionConstraint constraint,
      List<String> executables, {bool overwriteBinStubs}) {
    final completer0 = new Completer();
    scheduleMicrotask(() {
      try {
        _describeActive(name);
        _installInCache(
            new PackageDep(name, "hosted", constraint, name),
            executables,
            overwriteBinStubs: overwriteBinStubs).then((x0) {
          try {
            x0;
            completer0.complete(null);
          } catch (e0) {
            completer0.completeError(e0);
          }
        }, onError: (e1) {
          completer0.completeError(e1);
        });
      } catch (e2) {
        completer0.completeError(e2);
      }
    });
    return completer0.future;
  }
  Future activatePath(String path, List<String> executables,
      {bool overwriteBinStubs}) {
    final completer0 = new Completer();
    scheduleMicrotask(() {
      try {
        var entrypoint = new Entrypoint(path, cache);
        entrypoint.ensureLockFileIsUpToDate().then((x0) {
          try {
            x0;
            var name = entrypoint.root.name;
            _describeActive(name);
            var fullPath = canonicalize(entrypoint.root.dir);
            var id = new PackageId(
                name,
                "path",
                entrypoint.root.version,
                PathSource.describePath(fullPath));
            _writeLockFile(name, new LockFile([id]));
            var binDir = p.join(_directory, name, 'bin');
            join0() {
              _updateBinStubs(
                  entrypoint.root,
                  executables,
                  overwriteBinStubs: overwriteBinStubs);
              completer0.complete(null);
            }
            if (dirExists(binDir)) {
              deleteEntry(binDir);
              join0();
            } else {
              join0();
            }
          } catch (e0) {
            completer0.completeError(e0);
          }
        }, onError: (e1) {
          completer0.completeError(e1);
        });
      } catch (e2) {
        completer0.completeError(e2);
      }
    });
    return completer0.future;
  }
  Future _installInCache(PackageDep dep, List<String> executables,
      {bool overwriteBinStubs}) {
    final completer0 = new Completer();
    scheduleMicrotask(() {
      try {
        var source = cache.sources[dep.source];
        var root = new Package.inMemory(
            new Pubspec(
                "pub global activate",
                dependencies: [dep],
                sources: cache.sources));
        resolveVersions(SolveType.GET, cache.sources, root).then((x0) {
          try {
            var result = x0;
            join0() {
              result.showReport(SolveType.GET);
              Future.wait(result.packages.map(_cacheDependency)).then((x1) {
                try {
                  var ids = x1;
                  var lockFile = new LockFile(ids);
                  new Entrypoint.inMemory(
                      root,
                      lockFile,
                      cache).loadPackageGraph(result).then((x2) {
                    try {
                      var graph = x2;
                      _precompileExecutables(
                          graph.entrypoint,
                          dep.name).then((x3) {
                        try {
                          var snapshots = x3;
                          _writeLockFile(dep.name, lockFile);
                          _updateBinStubs(
                              graph.packages[dep.name],
                              executables,
                              overwriteBinStubs: overwriteBinStubs,
                              snapshots: snapshots);
                          completer0.complete(null);
                        } catch (e3) {
                          completer0.completeError(e3);
                        }
                      }, onError: (e4) {
                        completer0.completeError(e4);
                      });
                    } catch (e2) {
                      completer0.completeError(e2);
                    }
                  }, onError: (e5) {
                    completer0.completeError(e5);
                  });
                } catch (e1) {
                  completer0.completeError(e1);
                }
              }, onError: (e6) {
                completer0.completeError(e6);
              });
            }
            if (!result.succeeded) {
              join1() {
                join2() {
                  completer0.completeError(result.error);
                }
                if (result.error is NoVersionException) {
                  dataError(result.error.message);
                  join2();
                } else {
                  join2();
                }
              }
              if (result.error.package != dep.name) {
                completer0.completeError(result.error);
              } else {
                join1();
              }
            } else {
              join0();
            }
          } catch (e0) {
            completer0.completeError(e0);
          }
        }, onError: (e7) {
          completer0.completeError(e7);
        });
      } catch (e8) {
        completer0.completeError(e8);
      }
    });
    return completer0.future;
  }
  Future<Map<String, String>> _precompileExecutables(Entrypoint entrypoint,
      String package) {
    return log.progress("Precompiling executables", () {
      final completer0 = new Completer();
      scheduleMicrotask(() {
        try {
          var binDir = p.join(_directory, package, 'bin');
          cleanDir(binDir);
          entrypoint.loadPackageGraph().then((x0) {
            try {
              var graph = x0;
              AssetEnvironment.create(
                  entrypoint,
                  BarbackMode.RELEASE,
                  entrypoints: graph.packages[package].executableIds,
                  useDart2JS: false).then((x1) {
                try {
                  var environment = x1;
                  environment.barback.errors.listen(((error) {
                    log.error(log.red("Build error:\n$error"));
                  }));
                  completer0.complete(
                      environment.precompileExecutables(package, binDir));
                } catch (e1) {
                  completer0.completeError(e1);
                }
              }, onError: (e2) {
                completer0.completeError(e2);
              });
            } catch (e0) {
              completer0.completeError(e0);
            }
          }, onError: (e3) {
            completer0.completeError(e3);
          });
        } catch (e4) {
          completer0.completeError(e4);
        }
      });
      return completer0.future;
    });
  }
  Future<PackageId> _cacheDependency(PackageId id) {
    final completer0 = new Completer();
    scheduleMicrotask(() {
      try {
        var source = cache.sources[id.source];
        join0() {
          completer0.complete(source.resolveId(id));
        }
        if (!id.isRoot && source is CachedSource) {
          source.downloadToSystemCache(id).then((x0) {
            try {
              x0;
              join0();
            } catch (e0) {
              completer0.completeError(e0);
            }
          }, onError: (e1) {
            completer0.completeError(e1);
          });
        } else {
          join0();
        }
      } catch (e2) {
        completer0.completeError(e2);
      }
    });
    return completer0.future;
  }
  void _writeLockFile(String package, LockFile lockFile) {
    ensureDir(p.join(_directory, package));
    var oldPath = p.join(_directory, "$package.lock");
    if (fileExists(oldPath)) deleteEntry(oldPath);
    writeTextFile(
        _getLockFilePath(package),
        lockFile.serialize(cache.rootDir, cache.sources));
    var id = lockFile.packages[package];
    log.message('Activated ${_formatPackage(id)}.');
  }
  void _describeActive(String name) {
    try {
      var lockFile = new LockFile.load(_getLockFilePath(name), cache.sources);
      var id = lockFile.packages[name];
      if (id.source == 'git') {
        var url = GitSource.urlFromDescription(id.description);
        log.message(
            'Package ${log.bold(name)} is currently active from Git '
                'repository "${url}".');
      } else if (id.source == 'path') {
        var path = PathSource.pathFromDescription(id.description);
        log.message(
            'Package ${log.bold(name)} is currently active at path ' '"$path".');
      } else {
        log.message(
            'Package ${log.bold(name)} is currently active at version '
                '${log.bold(id.version)}.');
      }
    } on IOException catch (error) {
      return null;
    }
  }
  bool deactivate(String name) {
    var dir = p.join(_directory, name);
    if (!dirExists(dir)) return false;
    _deleteBinStubs(name);
    var lockFile = new LockFile.load(_getLockFilePath(name), cache.sources);
    var id = lockFile.packages[name];
    log.message('Deactivated package ${_formatPackage(id)}.');
    deleteEntry(dir);
    return true;
  }
  Future<Entrypoint> find(String name) {
    return new Future.sync(() {
      var lockFilePath = _getLockFilePath(name);
      var lockFile;
      try {
        lockFile = new LockFile.load(lockFilePath, cache.sources);
      } on IOException catch (error) {
        var oldLockFilePath = p.join(_directory, '$name.lock');
        try {
          lockFile = new LockFile.load(oldLockFilePath, cache.sources);
        } on IOException catch (error) {
          dataError("No active package ${log.bold(name)}.");
        }
        ensureDir(p.dirname(lockFilePath));
        new File(oldLockFilePath).renameSync(lockFilePath);
      }
      var id = lockFile.packages[name];
      lockFile.packages.remove(name);
      var source = cache.sources[id.source];
      if (source is CachedSource) {
        return cache.sources[id.source].getDirectory(
            id).then((dir) => new Package.load(name, dir, cache.sources)).then((package) {
          return new Entrypoint.inMemory(package, lockFile, cache);
        });
      }
      assert(id.source == "path");
      return new Entrypoint(
          PathSource.pathFromDescription(id.description),
          cache);
    });
  }
  Future<int> runExecutable(String package, String executable,
      Iterable<String> args, {BarbackMode mode}) {
    if (mode == null) mode = BarbackMode.RELEASE;
    var binDir = p.join(_directory, package, 'bin');
    if (mode != BarbackMode.RELEASE ||
        !fileExists(p.join(binDir, '$executable.dart.snapshot'))) {
      return find(package).then((entrypoint) {
        return exe.runExecutable(
            entrypoint,
            package,
            executable,
            args,
            mode: mode,
            isGlobal: true);
      });
    }
    if (log.verbosity == log.Verbosity.NORMAL) {
      log.verbosity = log.Verbosity.WARNING;
    }
    var snapshotPath = p.join(binDir, '$executable.dart.snapshot');
    return exe.runSnapshot(snapshotPath, args, recompile: () {
      log.fine(
          "$package:$executable is out of date and needs to be " "recompiled.");
      return find(
          package).then(
              (entrypoint) =>
                  entrypoint.loadPackageGraph()).then(
                      (graph) => _precompileExecutables(graph.entrypoint, package));
    });
  }
  String _getLockFilePath(String name) =>
      p.join(_directory, name, "pubspec.lock");
  void listActivePackages() {
    if (!dirExists(_directory)) return;
    loadPackageId(file, name) {
      var lockFile = new LockFile.load(p.join(_directory, file), cache.sources);
      return lockFile.packages[name];
    }
    var packages = listDir(_directory).map((entry) {
      if (fileExists(entry)) {
        return loadPackageId(entry, p.basenameWithoutExtension(entry));
      } else {
        return loadPackageId(p.join(entry, 'pubspec.lock'), p.basename(entry));
      }
    }).toList();
    packages
        ..sort((id1, id2) => id1.name.compareTo(id2.name))
        ..forEach((id) => log.message(_formatPackage(id)));
  }
  String _formatPackage(PackageId id) {
    if (id.source == 'git') {
      var url = GitSource.urlFromDescription(id.description);
      return '${log.bold(id.name)} ${id.version} from Git repository "$url"';
    } else if (id.source == 'path') {
      var path = PathSource.pathFromDescription(id.description);
      return '${log.bold(id.name)} ${id.version} at path "$path"';
    } else {
      return '${log.bold(id.name)} ${id.version}';
    }
  }
  void _updateBinStubs(Package package, List<String> executables,
      {bool overwriteBinStubs, Map<String, String> snapshots}) {
    if (snapshots == null) snapshots = const {};
    _deleteBinStubs(package.name);
    if ((executables != null && executables.isEmpty) ||
        package.pubspec.executables.isEmpty) {
      return;
    }
    ensureDir(_binStubDir);
    var installed = [];
    var collided = {};
    var allExecutables = ordered(package.pubspec.executables.keys);
    for (var executable in allExecutables) {
      if (executables != null && !executables.contains(executable)) continue;
      var script = package.pubspec.executables[executable];
      var previousPackage = _createBinStub(
          package,
          executable,
          script,
          overwrite: overwriteBinStubs,
          snapshot: snapshots[script]);
      if (previousPackage != null) {
        collided[executable] = previousPackage;
        if (!overwriteBinStubs) continue;
      }
      installed.add(executable);
    }
    if (installed.isNotEmpty) {
      var names = namedSequence("executable", installed.map(log.bold));
      log.message("Installed $names.");
    }
    if (collided.isNotEmpty) {
      for (var command in ordered(collided.keys)) {
        if (overwriteBinStubs) {
          log.warning(
              "Replaced ${log.bold(command)} previously installed from "
                  "${log.bold(collided[command])}.");
        } else {
          log.warning(
              "Executable ${log.bold(command)} was already installed "
                  "from ${log.bold(collided[command])}.");
        }
      }
      if (!overwriteBinStubs) {
        log.warning(
            "Deactivate the other package(s) or activate "
                "${log.bold(package.name)} using --overwrite.");
      }
    }
    if (executables != null) {
      var unknown = ordered(
          executables.where((exe) => !package.pubspec.executables.keys.contains(exe)));
      if (unknown.isNotEmpty) {
        dataError("Unknown ${namedSequence('executable', unknown)}.");
      }
    }
    var binFiles = package.listFiles(
        beneath: "bin",
        recursive: false).map((path) => package.relative(path)).toList();
    for (var executable in installed) {
      var script = package.pubspec.executables[executable];
      var scriptPath = p.join("bin", "$script.dart");
      if (!binFiles.contains(scriptPath)) {
        log.warning(
            'Warning: Executable "$executable" runs "$scriptPath", '
                'which was not found in ${log.bold(package.name)}.');
      }
    }
    if (installed.isNotEmpty) _suggestIfNotOnPath(installed);
  }
  String _createBinStub(Package package, String executable, String script,
      {bool overwrite, String snapshot}) {
    var binStubPath = p.join(_binStubDir, executable);
    if (Platform.operatingSystem == "windows") binStubPath += ".bat";
    var previousPackage;
    if (fileExists(binStubPath)) {
      var contents = readTextFile(binStubPath);
      var match = _binStubPackagePattern.firstMatch(contents);
      if (match != null) {
        previousPackage = match[1];
        if (!overwrite) return previousPackage;
      } else {
        log.fine("Could not parse binstub $binStubPath:\n$contents");
      }
    }
    var invocation;
    if (snapshot != null) {
      assert(p.isAbsolute(snapshot));
      invocation = 'dart "$snapshot"';
    } else {
      invocation = "pub global run ${package.name}:$script";
    }
    if (Platform.operatingSystem == "windows") {
      var batch = """
@echo off
rem This file was created by pub v${sdk.version}.
rem Package: ${package.name}
rem Version: ${package.version}
rem Executable: ${executable}
rem Script: ${script}
$invocation %*
""";
      writeTextFile(binStubPath, batch);
    } else {
      var bash = """
#!/usr/bin/env sh
# This file was created by pub v${sdk.version}.
# Package: ${package.name}
# Version: ${package.version}
# Executable: ${executable}
# Script: ${script}
$invocation "\$@"
""";
      writeTextFile(binStubPath, bash);
      var result = Process.runSync('chmod', ['+x', binStubPath]);
      if (result.exitCode != 0) {
        try {
          deleteEntry(binStubPath);
        } on IOException catch (err) {
          log.fine("Could not delete binstub:\n$err");
        }
        fail(
            'Could not make "$binStubPath" executable (exit code '
                '${result.exitCode}):\n${result.stderr}');
      }
    }
    return previousPackage;
  }
  void _deleteBinStubs(String package) {
    if (!dirExists(_binStubDir)) return;
    for (var file in listDir(_binStubDir, includeDirs: false)) {
      var contents = readTextFile(file);
      var match = _binStubPackagePattern.firstMatch(contents);
      if (match == null) {
        log.fine("Could not parse binstub $file:\n$contents");
        continue;
      }
      if (match[1] == package) {
        log.fine("Deleting old binstub $file");
        deleteEntry(file);
      }
    }
  }
  void _suggestIfNotOnPath(List<String> installed) {
    if (Platform.operatingSystem == "windows") {
      var result = runProcessSync("where", [r"\q", installed.first + ".bat"]);
      if (result.exitCode == 0) return;
      log.warning(
          "${log.yellow('Warning:')} Pub installs executables into "
              "${log.bold(_binStubDir)}, which is not on your path.\n"
              "You can fix that by adding that directory to your system's "
              '"Path" environment variable.\n'
              'A web search for "configure windows path" will show you how.');
    } else {
      var result = runProcessSync("which", [installed.first]);
      if (result.exitCode == 0) return;
      var binDir = _binStubDir;
      if (binDir.startsWith(Platform.environment['HOME'])) {
        binDir =
            p.join("~", p.relative(binDir, from: Platform.environment['HOME']));
      }
      log.warning(
          "${log.yellow('Warning:')} Pub installs executables into "
              "${log.bold(binDir)}, which is not on your path.\n"
              "You can fix that by adding this to your shell's config file "
              "(.bashrc, .bash_profile, etc.):\n" "\n"
              "  ${log.bold('export PATH="\$PATH":"$binDir"')}\n" "\n");
    }
  }
}
