Пример #1
0
        /// <summary>
        /// Uninstall <paramref name="package"/>, while still keeping the downloaded file in the cache.
        /// </summary>
        /// <remarks>It is safe to call it concurrently be cause we operations are done using the FileLock.</remarks>
        /// <param name="package">Package to uninstall.</param>
        public void UninstallPackage(NugetPackage package, ProgressReport progress)
        {
            using (GetLocalRepositoryLock())
            {
                currentProgressReport = progress;
                try
                {
                    manager.UninstallPackage(package.IPackage);

                    // Every time a new package is installed, we are updating the common targets
                    UpdateTargetsHelper();
                }
                finally
                {
                    currentProgressReport = null;
                }
            }
        }
Пример #2
0
        private static void RunPackageInstall(string packageInstall, string arguments, ProgressReport progress)
        {
            // Run packageinstall.exe
            using (var process = Process.Start(new ProcessStartInfo(packageInstall, arguments)
            {
                UseShellExecute = false,
                CreateNoWindow = true,
                RedirectStandardError = true,
                RedirectStandardOutput = true,
                WorkingDirectory = Path.GetDirectoryName(packageInstall),
            }))
            {
                if (process == null)
                {
                    throw new InvalidOperationException($"Could not start install package process [{packageInstall}] with options {arguments}");
                }

                var errorOutput = new StringBuilder();

                process.OutputDataReceived += (_, args) =>
                {
                    // Report progress
                    if (progress != null && !string.IsNullOrEmpty(args.Data))
                    {
                        var matches = powerShellProgressRegex.Match(args.Data);
                        int percentageResult;
                        if (matches.Success && int.TryParse(matches.Groups[1].Value, out percentageResult))
                        {
                            progress.UpdateProgress(percentageResult);
                        }
                    }
                };
                process.ErrorDataReceived += (_, args) =>
                {
                    if (!string.IsNullOrEmpty(args.Data))
                    {
                        // Save errors
                        lock (process)
                        {
                            errorOutput.AppendLine(args.Data);
                        }
                    }
                };

                // Process output and wait for exit
                process.BeginOutputReadLine();
                process.BeginErrorReadLine();
                process.WaitForExit();

                // Check exit code
                var exitCode = process.ExitCode;
                if (exitCode != 0)
                {
                    throw new InvalidOperationException($"Error code {exitCode} while running install package process [{packageInstall}]\n\n" + errorOutput);
                }
            }
        }
Пример #3
0
        /// <summary>
        /// Fetch, if not already downloaded, and install the package represented by
        /// (<paramref name="packageId"/>, <paramref name="version"/>).
        /// </summary>
        /// <remarks>It is safe to call it concurrently be cause we operations are done using the FileLock.</remarks>
        /// <param name="packageId">Name of package to install.</param>
        /// <param name="version">Version of package to install.</param>
        /// <param name="progress">Callbacks to report progress of downloads.</param>
        public async Task InstallPackage(string packageId, PackageVersion version, ProgressReport progress)
        {
            using (GetLocalRepositoryLock())
            {
                currentProgressReport = progress;
                try
                {
                    var package = manager.LocalRepository.FindPackage(packageId, version.ToSemanticVersion(), null, allowPrereleaseVersions: true, allowUnlisted: true);
                    if (package == null)
                    {
                        // Let's search in our cache
                        try
                        {
                            package = MachineCache.Default.FindPackage(packageId, version.ToSemanticVersion(), allowPrereleaseVersions: true, allowUnlisted: true);
                        }
                        catch (InvalidDataException)
                        {
                            // Package is somehow corrupted. We ignore this and  will redownload the file.
                        }
                        // It represents the name of the .nupkg in our cache
                        var sourceName = Path.Combine(CacheDirectory, PathResolver.GetPackageFileName(packageId, version.ToSemanticVersion()));
                        if (package == null)
                        {
                            // Always recreate cache in case it was deleted.
                            if (!Directory.Exists(CacheDirectory))
                            {
                                Directory.CreateDirectory(CacheDirectory);
                            }
                            package = manager.SourceRepository.FindPackage(packageId, version.ToSemanticVersion(), NullConstraintProvider.Instance, allowPrereleaseVersions: true, allowUnlisted: true);
                            if (package == null)
                            {
                                throw new ApplicationException("Cannot find package");
                            }

                            // Package has to be downloaded if it is a DataServicePackage which was not found in our cache.
                            if (package is DataServicePackage)
                            {
                                var downloadPackage = (DataServicePackage)package;
                                var url             = downloadPackage.DownloadUrl;
                                var client          = new WebClient();
                                var tcs             = new TaskCompletionSource <bool>();
                                progress?.UpdateProgress(ProgressAction.Download, 0);
                                client.DownloadProgressChanged += (o, e) => progress?.UpdateProgress(ProgressAction.Download, e.ProgressPercentage);
                                client.DownloadFileCompleted   += (o, e) => tcs.SetResult(true);
                                client.DownloadFileAsync(url, sourceName);
                                await tcs.Task;

                                progress?.UpdateProgress(ProgressAction.Download, 100);
                            }
                        }

                        progress?.UpdateProgress(ProgressAction.Install, -1);
                        manager.InstallPackage(package, ignoreDependencies: false, allowPrereleaseVersions: true);

                        OptimizedZipPackage.PurgeCache();
                    }

                    // Every time a new package is installed, we are updating the common targets
                    UpdateTargetsHelper();
                }
                finally
                {
                    currentProgressReport = null;
                }
            }
        }