コード例 #1
0
        // Deletes an empty folder from disk and the project
        private static void DeleteDirectory(IMSBuildProjectSystem projectSystem, string path)
        {
            var fullPath = Path.Combine(projectSystem.ProjectFullPath, path);

            if (!Directory.Exists(fullPath))
            {
                return;
            }

            // Only delete this folder if it is empty and we didn't specify that we want to recurse
            if (GetFiles(projectSystem, path, "*.*", recursive: false).Any() || GetDirectories(projectSystem, path).Any())
            {
                projectSystem.NuGetProjectContext.Log(MessageLevel.Warning, Strings.Warning_DirectoryNotEmpty, path);
                return;
            }
            projectSystem.RegisterProcessedFiles(new[] { path });

            projectSystem.DeleteDirectory(path, recursive: false);

            // Workaround for update-package TFS issue. If we're bound to TFS, do not try and delete directories.
            var sourceControlManager = SourceControlUtility.GetSourceControlManager(projectSystem.NuGetProjectContext);

            if (sourceControlManager != null)
            {
                // Source control bound, do not delete
                return;
            }

            // For potential project systems that do not remove items from disk, we delete the folder directly
            // There is no actual scenario where we know this is broken without the code below, but since the
            // code was always there, we are leaving it behind for now.
            if (!Directory.Exists(fullPath))
            {
                Directory.Delete(fullPath, recursive: false);

                // The directory is not guaranteed to be gone since there could be
                // other open handles. Wait, up to half a second, until the directory is gone.
                for (var i = 0; Directory.Exists(fullPath) && i < 5; ++i)
                {
                    Thread.Sleep(100);
                }

                projectSystem.RegisterProcessedFiles(new[] { path });

                projectSystem.NuGetProjectContext.Log(MessageLevel.Debug, Strings.Debug_RemovedFolder, fullPath);
            }
        }
コード例 #2
0
        internal static async Task DeleteFilesAsync(
            IMSBuildProjectSystem projectSystem,
            ZipArchive zipArchive,
            IEnumerable <string> otherPackagesPath,
            FrameworkSpecificGroup frameworkSpecificGroup,
            IDictionary <FileTransformExtensions, IPackageFileTransformer> fileTransformers,
            CancellationToken cancellationToken)
        {
            var packageTargetFramework = frameworkSpecificGroup.TargetFramework;
            IPackageFileTransformer transformer;

            var directoryLookup = frameworkSpecificGroup.Items.ToLookup(
                p => Path.GetDirectoryName(ResolveTargetPath(projectSystem,
                                                             fileTransformers,
                                                             fte => fte.UninstallExtension,
                                                             GetEffectivePathForContentFile(packageTargetFramework, p),
                                                             out transformer)));

            // Get all directories that this package may have added
            var directories = from grouping in directoryLookup
                              from directory in FileSystemUtility.GetDirectories(grouping.Key, altDirectorySeparator: false)
                              orderby directory.Length descending
                              select directory;

            var projectFullPath = projectSystem.ProjectFullPath;

            // Remove files from every directory
            foreach (var directory in directories)
            {
                var directoryFiles = directoryLookup.Contains(directory)
                    ? directoryLookup[directory]
                    : Enumerable.Empty <string>();

                if (!Directory.Exists(Path.Combine(projectFullPath, directory)))
                {
                    continue;
                }

                foreach (var file in directoryFiles)
                {
                    if (IsEmptyFolder(file))
                    {
                        continue;
                    }

                    // Resolve the path
                    var path = ResolveTargetPath(projectSystem,
                                                 fileTransformers,
                                                 fte => fte.UninstallExtension,
                                                 GetEffectivePathForContentFile(packageTargetFramework, file),
                                                 out transformer);

                    if (projectSystem.IsSupportedFile(path))
                    {
                        // Register the file being uninstalled (used by web site project system).
                        projectSystem.RegisterProcessedFiles(new[] { path });

                        if (transformer != null)
                        {
                            // TODO: use the framework from packages.config instead of the current framework
                            // which may have changed during re-targeting
                            var projectFramework = projectSystem.TargetFramework;

                            var matchingFiles = new List <InternalZipFileInfo>();
                            foreach (var otherPackagePath in otherPackagesPath)
                            {
                                using (var otherPackageZipReader = new PackageArchiveReader(otherPackagePath))
                                {
                                    // use the project framework to find the group that would have been installed
                                    var mostCompatibleContentFilesGroup = GetMostCompatibleGroup(
                                        projectFramework,
                                        otherPackageZipReader.GetContentItems());

                                    if (IsValid(mostCompatibleContentFilesGroup))
                                    {
                                        // Should not normalize content files group.
                                        // It should be like a ZipFileEntry with a forward slash.
                                        foreach (var otherPackageItem in mostCompatibleContentFilesGroup.Items)
                                        {
                                            if (GetEffectivePathForContentFile(packageTargetFramework,
                                                                               otherPackageItem)
                                                .Equals(
                                                    GetEffectivePathForContentFile(packageTargetFramework, file),
                                                    StringComparison.OrdinalIgnoreCase))
                                            {
                                                matchingFiles.Add(new InternalZipFileInfo(otherPackagePath,
                                                                                          otherPackageItem));
                                            }
                                        }
                                    }
                                }
                            }

                            try
                            {
                                var zipArchiveFileEntry = PathUtility.GetEntry(zipArchive, file);
                                if (zipArchiveFileEntry != null)
                                {
                                    await transformer.RevertFileAsync(
                                        () => Task.FromResult(zipArchiveFileEntry.Open()),
                                        path, matchingFiles,
                                        projectSystem,
                                        cancellationToken);
                                }
                            }
                            catch (Exception e)
                            {
                                projectSystem.NuGetProjectContext.Log(MessageLevel.Warning, e.Message);
                            }
                        }
                        else
                        {
                            try
                            {
                                var zipArchiveFileEntry = PathUtility.GetEntry(zipArchive, file);
                                if (zipArchiveFileEntry != null)
                                {
                                    await DeleteFileSafeAsync(
                                        path,
                                        () => Task.FromResult(zipArchiveFileEntry.Open()),
                                        projectSystem,
                                        cancellationToken);
                                }
                            }
                            catch (Exception e)
                            {
                                projectSystem.NuGetProjectContext.Log(MessageLevel.Warning, e.Message);
                            }
                        }
                    }
                }

                // If the directory is empty then delete it
                if (!GetFilesSafe(projectSystem, directory).Any() &&
                    !GetDirectoriesSafe(projectSystem, directory).Any())
                {
                    DeleteDirectorySafe(projectSystem, directory);
                }
            }
        }
コード例 #3
0
        internal static async Task AddFilesAsync(
            IMSBuildProjectSystem projectSystem,
            IAsyncPackageCoreReader packageReader,
            FrameworkSpecificGroup frameworkSpecificGroup,
            IDictionary <FileTransformExtensions, IPackageFileTransformer> fileTransformers,
            CancellationToken cancellationToken)
        {
            var packageTargetFramework = frameworkSpecificGroup.TargetFramework;

            var packageItemListAsArchiveEntryNames = frameworkSpecificGroup.Items.ToList();

            packageItemListAsArchiveEntryNames.Sort(new PackageItemComparer());

            try
            {
                var paths =
                    packageItemListAsArchiveEntryNames.Select(
                        file => ResolvePath(fileTransformers, fte => fte.InstallExtension,
                                            GetEffectivePathForContentFile(packageTargetFramework, file)));
                paths = paths.Where(p => !string.IsNullOrEmpty(p));

                projectSystem.RegisterProcessedFiles(paths);
            }
            catch (Exception)
            {
                // Ignore all exceptions for now
            }

            foreach (var file in packageItemListAsArchiveEntryNames)
            {
                if (IsEmptyFolder(file))
                {
                    continue;
                }

                var effectivePathForContentFile = GetEffectivePathForContentFile(packageTargetFramework, file);

                // Resolve the target path
                IPackageFileTransformer installTransformer;
                var path = ResolveTargetPath(projectSystem,
                                             fileTransformers,
                                             fte => fte.InstallExtension, effectivePathForContentFile, out installTransformer);

                if (projectSystem.IsSupportedFile(path))
                {
                    if (installTransformer != null)
                    {
                        await installTransformer.TransformFileAsync(
                            () => packageReader.GetStreamAsync(file, cancellationToken),
                            path,
                            projectSystem,
                            cancellationToken);
                    }
                    else
                    {
                        // Ignore uninstall transform file during installation
                        string truncatedPath;
                        var    uninstallTransformer =
                            FindFileTransformer(fileTransformers, fte => fte.UninstallExtension,
                                                effectivePathForContentFile, out truncatedPath);
                        if (uninstallTransformer != null)
                        {
                            continue;
                        }

                        await TryAddFileAsync(
                            projectSystem,
                            path,
                            () => packageReader.GetStreamAsync(file, cancellationToken),
                            cancellationToken);
                    }
                }
            }
        }