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; }
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); }
/// <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)); }