Example #1
0
        private PackageDef GetPackageDefFromRepo(List <IPackageRepository> repositories, string name, VersionSpecifier version)
        {
            if (name.ToLower().EndsWith(".tappackage"))
            {
                name = Path.GetFileNameWithoutExtension(name);
            }

            var specifier = new PackageSpecifier(name, version, CpuArchitecture.Unspecified, OperatingSystem.Current.ToString());
            var packages  = PackageRepositoryHelpers.GetPackagesFromAllRepos(repositories, specifier, InstalledPackages.Values.ToArray());

            if (packages.Any() == false)
            {
                packages = PackageRepositoryHelpers.GetPackagesFromAllRepos(repositories, specifier);
                if (packages.Any())
                {
                    log.Warning($"Unable to find a version of '{name}' package compatible with currently installed packages. Some installed packages may be upgraded.");
                }
            }

            return(packages.OrderByDescending(pkg => pkg.Version).FirstOrDefault(pkg => ArchitectureHelper.PluginsCompatible(pkg.Architecture, ArchitectureHelper.HostArchitecture)));
        }
Example #2
0
        protected override int LockedExecute(CancellationToken cancellationToken)
        {
            if (OutputPaths.Length > Packages.Length)
            {
                throw new Exception("More OutputPaths specified than packages. Exiting.");
            }

            string       destinationDir          = Target ?? Directory.GetCurrentDirectory();
            Installation destinationInstallation = new Installation(destinationDir);

            List <IPackageRepository> repositories = new List <IPackageRepository>();

            if (Repository == null)
            {
                repositories.AddRange(PackageManagerSettings.Current.Repositories.Where(p => p.IsEnabled).Select(s => s.Manager).ToList());
            }
            else
            {
                repositories.AddRange(Repository.Select(s => PackageRepositoryHelpers.DetermineRepositoryType(s)));
            }

            List <PackageDef> PackagesToDownload = PackageActionHelpers.GatherPackagesAndDependencyDefs(destinationInstallation, PackageReferences, Packages, Version, Architecture, OS, repositories, ForceInstall, InstallDependencies, false, false);

            if (PackagesToDownload == null)
            {
                return(2);
            }

            if (!DryRun)
            {
                // If OutputPaths are specified, download the specified packages to those locations before downloading the remaining files
                // Place the remaining files in the same location as the last named location
                for (int i = 0; i < OutputPaths.Length; i++)
                {
                    var outputPath  = OutputPaths[i];
                    var packageName = Packages[i];
                    var package     = PackagesToDownload.First(p =>
                                                               p.Name == packageName || (p.PackageSource is FilePackageDefSource s &&
                                                                                         s.PackageFilePath == Path.GetFullPath(packageName)));

                    string filename = null;

                    // Treat path as a directory if it ends with '/'
                    if (outputPath.EndsWith("/") || outputPath.EndsWith(Path.DirectorySeparatorChar.ToString()))
                    {
                        Directory.CreateDirectory(outputPath);
                    }
                    if (Directory.Exists(outputPath))
                    {
                        destinationDir = outputPath;
                    }
                    // Otherwise, treat it as a full path
                    else
                    {
                        var file = new FileInfo(outputPath);
                        destinationDir = file.DirectoryName;
                        Directory.CreateDirectory(destinationDir);
                        filename = file.FullName;
                    }

                    PackageActionHelpers.DownloadPackages(destinationDir, new List <PackageDef>()
                    {
                        package
                    },
                                                          new List <string>()
                    {
                        filename
                    });
                    PackagesToDownload.Remove(package);
                }

                // Download the remaining packages
                PackageActionHelpers.DownloadPackages(destinationDir, PackagesToDownload);
            }
            else
            {
                log.Info("Dry run completed. Specified packages are available.");
            }

            DownloadedPackages = PackagesToDownload;
            return(0);
        }
Example #3
0
        protected override int LockedExecute(CancellationToken cancellationToken)
        {
            if (OS == null)
            {
                switch (Environment.OSVersion.Platform)
                {
                case PlatformID.MacOSX:
                    OS = "OSX";
                    break;

                case PlatformID.Unix:
                    OS = "Linux";
                    break;

                default:
                    OS = "Windows";
                    break;
                }
            }

            List <IPackageRepository> repositories = new List <IPackageRepository>();

            if (Installed == false)
            {
                if (Repository == null)
                {
                    repositories.AddRange(PackageManagerSettings.Current.Repositories.Where(p => p.IsEnabled).Select(s => s.Manager));
                }
                else
                {
                    repositories.AddRange(Repository.Select(s => PackageRepositoryHelpers.DetermineRepositoryType(s)));
                }
            }

            if (Target == null)
            {
                Target = FileSystemHelper.GetCurrentInstallationDirectory();
            }

            HashSet <PackageDef> installed = new Installation(Target).GetPackages().ToHashSet();


            VersionSpecifier versionSpec = VersionSpecifier.Parse("^");

            if (!String.IsNullOrWhiteSpace(Version))
            {
                versionSpec = VersionSpecifier.Parse(Version);
            }

            if (string.IsNullOrEmpty(Name))
            {
                var packages = installed.ToList();
                packages.AddRange(PackageRepositoryHelpers.GetPackageNameAndVersionFromAllRepos(repositories, new PackageSpecifier("", versionSpec, Architecture, OS)));

                if (Installed)
                {
                    packages = packages.Where(p => installed.Any(i => i.Name == p.Name)).ToList();
                }

                PrintReadable(packages, installed);
            }
            else
            {
                IPackageIdentifier package = installed.FirstOrDefault(p => p.Name == Name);

                if (Installed)
                {
                    if (package is null)
                    {
                        log.Info($"{Name} is not installed");
                        return(-1);
                    }

                    log.Info(package.Version.ToString());
                    return(0);
                }


                List <PackageVersion> versions = null;

                if (All)
                {
                    versions = PackageRepositoryHelpers.GetAllVersionsFromAllRepos(repositories, Name).Distinct().ToList();
                    var versionsCount = versions.Count;
                    if (versionsCount == 0) // No versions
                    {
                        log.Info($"No versions of '{Name}'.");
                        return(0);
                    }

                    if (Version != null) // Version is specified by user
                    {
                        versions = versions.Where(v => versionSpec.IsCompatible(v.Version)).ToList();
                    }

                    if (versions.Any() == false && versionsCount > 0)
                    {
                        log.Info($"Package '{Name}' does not exists with version '{Version}'.");
                        log.Info($"Package '{Name}' exists in {versionsCount} other versions, please specify a different version.");
                        return(0);
                    }
                }
                else
                {
                    var opentap = new Installation(Target).GetOpenTapPackage();
                    versions = PackageRepositoryHelpers.GetAllVersionsFromAllRepos(repositories, Name, opentap).Distinct().ToList();

                    versions = versions.Where(s => s.IsPlatformCompatible(Architecture, OS)).ToList();

                    if (versions.Any() == false) // No compatible versions
                    {
                        versions = PackageRepositoryHelpers.GetAllVersionsFromAllRepos(repositories, Name).ToList();
                        if (versions.Any())
                        {
                            log.Warning($"There are no compatible versions of '{Name}'.");
                            log.Info($"There are {versions.Count} incompatible versions available. Use '--all' to show these.");
                        }
                        else
                        {
                            log.Warning($"Package '{Name}' could not be found in any repository.");
                        }

                        return(0);
                    }


                    versions = versions.Where(v => versionSpec.IsCompatible(v.Version)).ToList();
                    if (versions.Any() == false) // No versions that are compatible
                    {
                        if (string.IsNullOrEmpty(Version))
                        {
                            log.Warning($"There are no released versions of '{Name}'.");
                        }
                        else
                        {
                            log.Warning($"Package '{Name}' does not exists with version '{Version}'.");
                        }

                        var anyPrereleaseSpecifier = new VersionSpecifier(versionSpec.Major, versionSpec.Minor, versionSpec.Patch, versionSpec.PreRelease, versionSpec.BuildMetadata, VersionMatchBehavior.AnyPrerelease | versionSpec.MatchBehavior);
                        versions = versions.Where(v => anyPrereleaseSpecifier.IsCompatible(v.Version)).ToList();
                        if (versions.Any())
                        {
                            log.Info($"There are {versions.Count} pre-released versions available. Use '--version <pre-release>' (e.g. '--version rc') or '--all' to show these.");
                        }

                        return(0);
                    }
                }
                PrintVersionsReadable(package, versions);
            }
            return(0);
        }
Example #4
0
        internal static PackageDef FindPackage(PackageSpecifier packageReference, bool force, Installation installation, List <IPackageRepository> repositories)
        {
            IPackageIdentifier[] compatibleWith;
            if (!force)
            {
                var tapPackage = installation.GetOpenTapPackage();
                if (tapPackage != null)
                {
                    compatibleWith = new[] { installation.GetOpenTapPackage() }
                }
                ;
                else
                {
                    compatibleWith = new[] { new PackageIdentifier("OpenTAP", PluginManager.GetOpenTapAssembly().SemanticVersion.ToString(), CpuArchitecture.Unspecified, "") }
                };
            }
            else
            {
                compatibleWith = Array.Empty <IPackageIdentifier>();
            }

            var compatiblePackages = PackageRepositoryHelpers.GetPackagesFromAllRepos(repositories, packageReference, compatibleWith);

            // Of the compatible packages, pick the one with the highest version number. If that package is available from several repositories, pick the one with the lowest index in the list in PackageManagerSettings
            PackageDef package = null;

            if (compatiblePackages.Any())
            {
                package = compatiblePackages.GroupBy(p => p.Version).OrderByDescending(g => g.Key).FirstOrDefault()
                          .OrderBy(p => repositories.IndexWhen(e => NormalizeRepoUrl(e.Url) == NormalizeRepoUrl((p.PackageSource as IRepositoryPackageDefSource)?.RepositoryUrl))).FirstOrDefault();
            }

            // If no package was found, try to figure out why
            if (package == null)
            {
                var compatibleVersions = PackageRepositoryHelpers.GetAllVersionsFromAllRepos(repositories, packageReference.Name, compatibleWith);
                var versions           = PackageRepositoryHelpers.GetAllVersionsFromAllRepos(repositories, packageReference.Name);

                // Any packages compatible with opentap and platform
                var filteredVersions = compatibleVersions.Where(v => v.IsPlatformCompatible(packageReference.Architecture, packageReference.OS)).ToList();
                if (filteredVersions.Any())
                {
                    // if the specified version exist, don't say it could not be found.
                    if (versions.Any(v => packageReference.Version.IsCompatible(v.Version)))
                    {
                        throw new ExitCodeException(1, $"Package '{packageReference.Name}' matching version '{packageReference.Version}' is not compatible. Latest compatible version is '{filteredVersions.FirstOrDefault().Version}'.");
                    }
                    else
                    {
                        throw new ExitCodeException(1, $"Package '{packageReference.Name}' matching version '{packageReference.Version}' could not be found. Latest compatible version is '{filteredVersions.FirstOrDefault().Version}'.");
                    }
                }

                // Any compatible with platform but not opentap
                filteredVersions = versions.Where(v => v.IsPlatformCompatible(packageReference.Architecture, packageReference.OS)).ToList();
                if (filteredVersions.Any() && compatibleWith.Any())
                {
                    var opentapPackage = compatibleWith.First();
                    throw new ExitCodeException(1, $"Package '{packageReference.Name}' does not exist in a version compatible with '{opentapPackage.Name}' version '{opentapPackage.Version}'.");
                }

                // Any compatible with opentap but not platform
                if (compatibleVersions.Any())
                {
                    if (packageReference.Version != VersionSpecifier.Any || packageReference.OS != null || packageReference.Architecture != CpuArchitecture.Unspecified)
                    {
                        throw new ExitCodeException(1,
                                                    string.Format("No '{0}' package {1} was found.", packageReference.Name, string.Join(" and ",
                                                                                                                                        new string[] {
                            packageReference.Version != VersionSpecifier.Any ? $"compatible with version '{packageReference.Version}'": null,
                            packageReference.OS != null ? $"compatible with '{packageReference.OS}' operating system" : null,
                            packageReference.Architecture != CpuArchitecture.Unspecified ? $"with '{packageReference.Architecture}' architecture" : null
                        }.Where(x => x != null).ToArray())));
                    }
                    else
                    {
                        throw new ExitCodeException(1, $"Package '{packageReference.Name}' does not exist in a version compatible with this OS and architecture.");
                    }
                }

                // Any version
                if (versions.Any())
                {
                    var opentapPackage = compatibleWith.FirstOrDefault();
                    if (opentapPackage != null)
                    {
                        throw new ExitCodeException(1, $"Package '{packageReference.Name}' does not exist in a version compatible with this OS, architecture and '{opentapPackage.Name}' version '{opentapPackage.Version}'.");
                    }
                    else
                    {
                        throw new ExitCodeException(1, $"Package '{packageReference.Name}' does not exist in a version compatible with this OS and architecture.");
                    }
                }

                throw new ExitCodeException(1, $"Package '{packageReference.Name}' could not be found in any repository.");
            }
            return(package);
        }
Example #5
0
        internal static List <string> DownloadPackages(string destinationDir, List <PackageDef> PackagesToDownload, List <string> filenames = null)
        {
            List <string> downloadedPackages = new List <string>();

            for (int i = 0; i < PackagesToDownload.Count; i++)
            {
                Stopwatch timer = Stopwatch.StartNew();

                var    pkg      = PackagesToDownload[i];
                string filename = filenames?.ElementAtOrDefault(i) ?? Path.Combine(destinationDir, GetQualifiedFileName(pkg));

                TapThread.ThrowIfAborted();

                try
                {
                    PackageDef existingPkg = null;
                    try
                    {
                        // If the package we are installing is from a file, we should always use that file instead of a cached package.
                        // During development a package might not change version but still have different content.
                        if (pkg.PackageSource is FilePackageDefSource == false && File.Exists(filename))
                        {
                            existingPkg = PackageDef.FromPackage(filename);
                        }
                    }
                    catch (Exception e)
                    {
                        log.Warning("Could not open OpenTAP Package. Redownloading package.", e);
                        File.Delete(filename);
                    }

                    if (existingPkg != null)
                    {
                        if (existingPkg.Version == pkg.Version && existingPkg.OS == pkg.OS && existingPkg.Architecture == pkg.Architecture)
                        {
                            if (!PackageCacheHelper.PackageIsFromCache(existingPkg))
                            {
                                log.Info("Package '{0}' already exists in '{1}'.", pkg.Name, destinationDir);
                            }
                            else
                            {
                                log.Info("Package '{0}' already exists in cache '{1}'.", pkg.Name, destinationDir);
                            }
                        }
                        else
                        {
                            throw new Exception($"A package already exists but it is not the same as the package that is being downloaded.");
                        }
                    }
                    else
                    {
                        string source = (pkg.PackageSource as IRepositoryPackageDefSource)?.RepositoryUrl;
                        if (source == null && pkg.PackageSource is FilePackageDefSource fileSource)
                        {
                            source = fileSource.PackageFilePath;
                        }

                        IPackageRepository rm = PackageRepositoryHelpers.DetermineRepositoryType(source);
                        if (PackageCacheHelper.PackageIsFromCache(pkg))
                        {
                            rm.DownloadPackage(pkg, filename);
                            log.Info(timer, "Found package '{0}' in cache. Copied to '{1}'.", pkg.Name, Path.GetFullPath(filename));
                        }
                        else
                        {
                            log.Debug("Downloading '{0}' version '{1}' from '{2}'", pkg.Name, pkg.Version, source);
                            rm.DownloadPackage(pkg, filename);
                            log.Info(timer, "Downloaded '{0}' to '{1}'.", pkg.Name, Path.GetFullPath(filename));
                            PackageCacheHelper.CachePackage(filename);
                        }
                    }
                }
                catch (Exception ex)
                {
                    log.Error("Failed to download OpenTAP package.");
                    throw ex;
                }

                downloadedPackages.Add(filename);
            }

            return(downloadedPackages);
        }