Ejemplo n.º 1
0
        public async Task AddPackageAsync(PackageInput packageInput)
        {
            // Add nupkg
            var nupkgFile = _context.Source.Get(GetNupkgPath(packageInput.Identity));

            await nupkgFile.Write(File.OpenRead(packageInput.PackagePath), _context.Log, _context.Token);

            // Add nuspec
            var nuspecPath = $"{packageInput.Identity.Id}.nuspec".ToLowerInvariant();

            var nuspecEntry = await packageInput.RunWithLockAsync((p) => Task.FromResult(p.Zip.Entries
                                                                                         .Where(entry => entry.FullName.Equals(nuspecPath, StringComparison.OrdinalIgnoreCase))
                                                                                         .FirstOrDefault()));

            if (nuspecEntry == null)
            {
                throw new InvalidDataException($"Unable to find '{nuspecPath}'. Path: '{packageInput.PackagePath}'.");
            }

            var nuspecStream = await packageInput.RunWithLockAsync(async p => await nuspecEntry.Open().AsMemoryStreamAsync());

            using (nuspecStream)
            {
                var entryFile = _context.Source.Get(GetZipFileUri(packageInput.Identity, nuspecPath));
                await entryFile.Write(nuspecStream, _context.Log, _context.Token);
            }

            // Update index
            var indexFile = _context.Source.Get(GetIndexUri(packageInput.Identity.Id));

            var versions = await GetVersions(packageInput.Identity.Id);

            versions.Add(packageInput.Identity.Version);

            var indexJson = CreateIndex(versions);

            await indexFile.Write(indexJson, _context.Log, _context.Token);

            // Set nupkg url
            packageInput.NupkgUri = nupkgFile.EntityUri;
        }
Ejemplo n.º 2
0
        private async Task <List <PackageFile> > GetAssembliesAsync(PackageInput packageInput)
        {
            var result = new List <PackageFile>();
            var seen   = new HashSet <ISleetFile>();

            var assemblyFiles = await packageInput.RunWithLockAsync(p => Task.FromResult(p.Zip.Entries
                                                                                         .Where(e => e.FullName.EndsWith(".dll", StringComparison.OrdinalIgnoreCase))
                                                                                         .ToList()));

            var pdbFiles = await packageInput.RunWithLockAsync(p => Task.FromResult(p.Zip.Entries
                                                                                    .Where(e => e.FullName.EndsWith(".pdb", StringComparison.OrdinalIgnoreCase))
                                                                                    .ToList()));

            foreach (var assembly in assemblyFiles)
            {
                string          assemblyHash = null;
                string          pdbHash      = null;
                ZipArchiveEntry pdbEntry     = null;
                var             valid        = false;

                try
                {
                    using (var stream = await packageInput.GetEntryStreamWithLockAsync(assembly))
                        using (var reader = new PEReader(stream))
                        {
                            assemblyHash = SymbolsUtility.GetSymbolHashFromAssembly(reader);
                            pdbHash      = SymbolsUtility.GetPDBHashFromAssembly(reader);
                        }

                    var assemblyWithoutExt = SleetLib.PathUtility.GetFullPathWithoutExtension(assembly.FullName);

                    pdbEntry = pdbFiles.FirstOrDefault(e =>
                                                       StringComparer.OrdinalIgnoreCase.Equals(
                                                           SleetLib.PathUtility.GetFullPathWithoutExtension(e.FullName), assemblyWithoutExt));

                    valid = true;
                }
                catch
                {
                    // Ignore bad assemblies
                    var message = LogMessage.Create(LogLevel.Warning, $"Unable add symbols for {assembly.FullName}, this file will not be present in the symbol server.");
                    await _context.Log.LogAsync(message);
                }

                if (valid)
                {
                    // Add .dll
                    var fileInfo  = new FileInfo(assembly.FullName);
                    var dllFile   = _context.Source.Get(SymbolsIndexUtility.GetAssemblyFilePath(fileInfo.Name, assemblyHash));
                    var indexFile = _context.Source.Get(SymbolsIndexUtility.GetAssemblyToPackageIndexPath(fileInfo.Name, assemblyHash));

                    // Avoid duplicates
                    if (seen.Add(dllFile))
                    {
                        result.Add(new PackageFile(fileInfo.Name, assemblyHash, assembly, dllFile, indexFile));
                    }

                    // Add .pdb
                    if (pdbEntry != null)
                    {
                        var pdbFileInfo  = new FileInfo(pdbEntry.FullName);
                        var pdbFile      = _context.Source.Get(SymbolsIndexUtility.GetAssemblyFilePath(pdbFileInfo.Name, pdbHash));
                        var pdbIndexFile = _context.Source.Get(SymbolsIndexUtility.GetAssemblyToPackageIndexPath(pdbFileInfo.Name, pdbHash));

                        // Avoid duplicates
                        if (seen.Add(pdbFile))
                        {
                            result.Add(new PackageFile(pdbFileInfo.Name, pdbHash, pdbEntry, pdbFile, pdbIndexFile));
                        }
                    }
                }
            }

            return(result);
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Create a PackageDetails page that contains all the package information and an exact uri.
        /// </summary>
        public static async Task <JObject> CreatePackageDetailsWithExactUriAsync(PackageInput packageInput, Uri detailsUri, Guid commitId, bool writeFileList)
        {
            var now          = DateTimeOffset.UtcNow;
            var nuspecReader = await packageInput.RunWithLockAsync(async (p) => await p.Package.GetNuspecReaderAsync(CancellationToken.None));

            var json = JsonUtility.Create(detailsUri, new List <string>()
            {
                "PackageDetails", "catalog:Permalink"
            });

            json.Add("commitId", commitId.ToString().ToLowerInvariant());
            json.Add("commitTimeStamp", DateTimeOffset.UtcNow.GetDateString());
            json.Add("sleet:operation", "add");

            var context = await JsonUtility.GetContextAsync("Catalog");

            json.Add("@context", context);

            json.Add("id", packageInput.Identity.Id);
            json.Add("version", packageInput.Identity.Version.ToFullVersionString());

            json.Add("created", now.GetDateString());
            json.Add("lastEdited", "0001-01-01T00:00:00Z");

            var copyProperties = new List <string>()
            {
                "authors",
                "copyright",
                "description",
                "iconUrl",
                "projectUrl",
                "licenseUrl",
                "language",
                "summary",
                "owners",
                "releaseNotes"
            };

            foreach (var propertyName in copyProperties)
            {
                json.Add(CreateProperty(propertyName, propertyName, nuspecReader));
            }

            json.Add("isPrerelease", packageInput.Identity.Version.IsPrerelease);

            // Unused?
            json.Add("licenseNames", string.Empty);
            json.Add("licenseReportUrl", string.Empty);

            // All packages are listed
            json.Add("listed", true);

            var titleValue = GetEntry(nuspecReader, "title");

            if (!string.IsNullOrEmpty(titleValue))
            {
                json.Add("title", titleValue);
            }

            using (var stream = File.OpenRead(packageInput.PackagePath))
            {
                using (var sha512 = SHA512.Create())
                {
                    var packageHash = Convert.ToBase64String(sha512.ComputeHash(stream));

                    json.Add("packageHash", packageHash);
                    json.Add("packageHashAlgorithm", "SHA512");
                }

                json.Add("packageSize", stream.Length);
            }

            json.Add("published", now.GetDateString());
            json.Add("requireLicenseAcceptance", GetEntry(nuspecReader, "requireLicenseAcceptance").Equals("true", StringComparison.OrdinalIgnoreCase));

            var minVersion = nuspecReader.GetMinClientVersion();

            if (minVersion != null)
            {
                json.Add("minClientVersion", minVersion.ToIdentityString());
            }

            // Tags
            var tagSet = new HashSet <string>(GetEntry(nuspecReader, "tags").Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries), StringComparer.OrdinalIgnoreCase);

            tagSet.Remove(string.Empty);
            var tagArray = new JArray(tagSet);

            json.Add("tags", tagArray);

            // Framework assemblies
            var fwrGroups = nuspecReader.GetFrameworkReferenceGroups();
            var fwrArray  = new JArray();

            json.Add("frameworkAssemblyGroup", fwrArray);

            foreach (var group in fwrGroups.OrderBy(e => e.TargetFramework.GetShortFolderName(), StringComparer.OrdinalIgnoreCase))
            {
                var groupTFM  = group.TargetFramework.GetShortFolderName().ToLowerInvariant();
                var groupNode = JsonUtility.Create(detailsUri, $"frameworkassemblygroup/{groupTFM}".ToLowerInvariant(), "FrameworkAssemblyGroup");

                // Leave the framework property out for the 'any' group
                if (!group.TargetFramework.IsAny)
                {
                    groupNode.Add("targetFramework", groupTFM);
                }

                fwrArray.Add(groupNode);

                if (group.Items.Any())
                {
                    var assemblyArray = new JArray();
                    groupNode.Add("assembly", assemblyArray);

                    foreach (var fwAssembly in group.Items.Distinct().OrderBy(e => e, StringComparer.OrdinalIgnoreCase))
                    {
                        assemblyArray.Add(fwAssembly);
                    }
                }
            }

            // Dependencies
            var dependencyGroups = nuspecReader.GetDependencyGroups();

            var depArray = new JArray();

            json.Add("dependencyGroups", depArray);

            foreach (var group in dependencyGroups.OrderBy(e => e.TargetFramework.GetShortFolderName(), StringComparer.OrdinalIgnoreCase))
            {
                var groupTFM  = group.TargetFramework.GetShortFolderName().ToLowerInvariant();
                var groupNode = JsonUtility.Create(detailsUri, $"dependencygroup/{groupTFM}".ToLowerInvariant(), "PackageDependencyGroup");

                // Leave the framework property out for the 'any' group
                if (!group.TargetFramework.IsAny)
                {
                    groupNode.Add("targetFramework", groupTFM);
                }

                depArray.Add(groupNode);

                if (group.Packages.Any())
                {
                    var packageArray = new JArray();
                    groupNode.Add("dependencies", packageArray);

                    foreach (var depPackage in group.Packages.Distinct().OrderBy(e => e.Id, StringComparer.OrdinalIgnoreCase))
                    {
                        var packageNode = JsonUtility.Create(detailsUri, $"dependencygroup/{groupTFM}/{depPackage.Id}".ToLowerInvariant(), "PackageDependency");
                        packageNode.Add("id", depPackage.Id);
                        packageNode.Add("range", depPackage.VersionRange.ToNormalizedString());

                        packageArray.Add(packageNode);
                    }
                }
            }

            json.Add("packageContent", packageInput.NupkgUri.AbsoluteUri);

            if (writeFileList)
            {
                // Write out all files contained in the package
                var packageEntriesArray = new JArray();
                json.Add("packageEntries", packageEntriesArray);

                await packageInput.RunWithLockAsync(p => AddZipEntry(p, detailsUri, packageEntriesArray));
            }

            json.Add("sleet:toolVersion", AssemblyVersionHelper.GetVersion().ToFullVersionString());

            return(JsonLDTokenComparer.Format(json));
        }