| Index: sdk/lib/_internal/pub_generated/lib/src/source/git.dart
|
| diff --git a/sdk/lib/_internal/pub_generated/lib/src/source/git.dart b/sdk/lib/_internal/pub_generated/lib/src/source/git.dart
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..5a04d1224d4f8310240c87560a1d2f080fedb505
|
| --- /dev/null
|
| +++ b/sdk/lib/_internal/pub_generated/lib/src/source/git.dart
|
| @@ -0,0 +1,194 @@
|
| +library pub.source.git;
|
| +import 'dart:async';
|
| +import 'package:path/path.dart' as path;
|
| +import '../git.dart' as git;
|
| +import '../io.dart';
|
| +import '../log.dart' as log;
|
| +import '../package.dart';
|
| +import '../pubspec.dart';
|
| +import '../utils.dart';
|
| +import 'cached.dart';
|
| +class GitSource extends CachedSource {
|
| + static String urlFromDescription(description) => description["url"];
|
| + final name = "git";
|
| + final _updatedRepos = new Set<String>();
|
| + Future<String> getPackageNameFromRepo(String repo) {
|
| + return withTempDir((tempDir) {
|
| + return _clone(repo, tempDir, shallow: true).then((_) {
|
| + var pubspec = new Pubspec.load(tempDir, systemCache.sources);
|
| + return pubspec.name;
|
| + });
|
| + });
|
| + }
|
| + Future<Pubspec> describeUncached(PackageId id) {
|
| + return downloadToSystemCache(id).then((package) => package.pubspec);
|
| + }
|
| + Future<Package> downloadToSystemCache(PackageId id) {
|
| + var revisionCachePath;
|
| + if (!git.isInstalled) {
|
| + fail(
|
| + "Cannot get ${id.name} from Git (${_getUrl(id)}).\n"
|
| + "Please ensure Git is correctly installed.");
|
| + }
|
| + ensureDir(path.join(systemCacheRoot, 'cache'));
|
| + return _ensureRevision(id).then((_) => getDirectory(id)).then((path) {
|
| + revisionCachePath = path;
|
| + if (entryExists(revisionCachePath)) return null;
|
| + return _clone(_repoCachePath(id), revisionCachePath, mirror: false);
|
| + }).then((_) {
|
| + var ref = _getEffectiveRef(id);
|
| + if (ref == 'HEAD') return null;
|
| + return _checkOut(revisionCachePath, ref);
|
| + }).then((_) {
|
| + return new Package.load(id.name, revisionCachePath, systemCache.sources);
|
| + });
|
| + }
|
| + Future<String> getDirectory(PackageId id) {
|
| + return _ensureRevision(id).then((rev) {
|
| + var revisionCacheName = '${id.name}-$rev';
|
| + return path.join(systemCacheRoot, revisionCacheName);
|
| + });
|
| + }
|
| + dynamic parseDescription(String containingPath, description,
|
| + {bool fromLockFile: false}) {
|
| + if (description is String) return description;
|
| + if (description is! Map || !description.containsKey('url')) {
|
| + throw new FormatException(
|
| + "The description must be a Git URL or a map " "with a 'url' key.");
|
| + }
|
| + var parsed = new Map.from(description);
|
| + parsed.remove('url');
|
| + parsed.remove('ref');
|
| + if (fromLockFile) parsed.remove('resolved-ref');
|
| + if (!parsed.isEmpty) {
|
| + var plural = parsed.length > 1;
|
| + var keys = parsed.keys.join(', ');
|
| + throw new FormatException("Invalid key${plural ? 's' : ''}: $keys.");
|
| + }
|
| + return description;
|
| + }
|
| + bool descriptionsEqual(description1, description2) {
|
| + return _getUrl(description1) == _getUrl(description2) &&
|
| + _getRef(description1) == _getRef(description2);
|
| + }
|
| + Future<PackageId> resolveId(PackageId id) {
|
| + return _ensureRevision(id).then((revision) {
|
| + var description = {
|
| + 'url': _getUrl(id),
|
| + 'ref': _getRef(id)
|
| + };
|
| + description['resolved-ref'] = revision;
|
| + return new PackageId(id.name, name, id.version, description);
|
| + });
|
| + }
|
| + List<Package> getCachedPackages() {
|
| + throw new UnimplementedError(
|
| + "The git source doesn't support listing its cached packages yet.");
|
| + }
|
| + Future<Pair<int, int>> repairCachedPackages() {
|
| + if (!dirExists(systemCacheRoot)) return new Future.value(new Pair(0, 0));
|
| + var successes = 0;
|
| + var failures = 0;
|
| + var packages = listDir(
|
| + systemCacheRoot).where(
|
| + (entry) =>
|
| + dirExists(
|
| + path.join(
|
| + entry,
|
| + ".git"))).map(
|
| + (packageDir) =>
|
| + new Package.load(null, packageDir, systemCache.sources)).toList();
|
| + packages.sort(Package.orderByNameAndVersion);
|
| + return Future.wait(packages.map((package) {
|
| + log.message(
|
| + "Resetting Git repository for "
|
| + "${log.bold(package.name)} ${package.version}...");
|
| + return git.run(
|
| + ["clean", "-d", "--force", "-x"],
|
| + workingDir: package.dir).then((_) {
|
| + return git.run(["reset", "--hard", "HEAD"], workingDir: package.dir);
|
| + }).then((_) {
|
| + successes++;
|
| + }).catchError((error, stackTrace) {
|
| + failures++;
|
| + log.error(
|
| + "Failed to reset ${log.bold(package.name)} "
|
| + "${package.version}. Error:\n$error");
|
| + log.fine(stackTrace);
|
| + failures++;
|
| + }, test: (error) => error is git.GitException);
|
| + })).then((_) => new Pair(successes, failures));
|
| + }
|
| + Future<String> _ensureRevision(PackageId id) {
|
| + return syncFuture(() {
|
| + var path = _repoCachePath(id);
|
| + if (!entryExists(path)) {
|
| + return _clone(
|
| + _getUrl(id),
|
| + path,
|
| + mirror: true).then((_) => _revParse(id));
|
| + }
|
| + var description = id.description;
|
| + if (description is! Map || !description.containsKey('resolved-ref')) {
|
| + return _updateRepoCache(id).then((_) => _revParse(id));
|
| + }
|
| + return _revParse(id).catchError((error) {
|
| + if (error is! git.GitException) throw error;
|
| + return _updateRepoCache(id).then((_) => _revParse(id));
|
| + });
|
| + });
|
| + }
|
| + Future _updateRepoCache(PackageId id) {
|
| + var path = _repoCachePath(id);
|
| + if (_updatedRepos.contains(path)) return new Future.value();
|
| + return git.run(["fetch"], workingDir: path).then((_) {
|
| + _updatedRepos.add(path);
|
| + });
|
| + }
|
| + Future<String> _revParse(PackageId id) {
|
| + return git.run(
|
| + ["rev-parse", _getEffectiveRef(id)],
|
| + workingDir: _repoCachePath(id)).then((result) => result.first);
|
| + }
|
| + Future _clone(String from, String to, {bool mirror: false, bool shallow:
|
| + false}) {
|
| + return syncFuture(() {
|
| + ensureDir(to);
|
| + var args = ["clone", from, to];
|
| + if (mirror) args.insert(1, "--mirror");
|
| + if (shallow) args.insertAll(1, ["--depth", "1"]);
|
| + return git.run(args);
|
| + }).then((result) => null);
|
| + }
|
| + Future _checkOut(String repoPath, String ref) {
|
| + return git.run(
|
| + ["checkout", ref],
|
| + workingDir: repoPath).then((result) => null);
|
| + }
|
| + String _repoCachePath(PackageId id) {
|
| + var repoCacheName = '${id.name}-${sha1(_getUrl(id))}';
|
| + return path.join(systemCacheRoot, 'cache', repoCacheName);
|
| + }
|
| + String _getUrl(description) {
|
| + description = _getDescription(description);
|
| + if (description is String) return description;
|
| + return description['url'];
|
| + }
|
| + String _getEffectiveRef(description) {
|
| + description = _getDescription(description);
|
| + if (description is Map && description.containsKey('resolved-ref')) {
|
| + return description['resolved-ref'];
|
| + }
|
| + var ref = _getRef(description);
|
| + return ref == null ? 'HEAD' : ref;
|
| + }
|
| + String _getRef(description) {
|
| + description = _getDescription(description);
|
| + if (description is String) return null;
|
| + return description['ref'];
|
| + }
|
| + _getDescription(description) {
|
| + if (description is PackageId) return description.description;
|
| + return description;
|
| + }
|
| +}
|
|
|