private bool ValidateCgManifestFile(string generatedCgManifest) { // Validation of existing cgmainfest.json results in failure due to mismatch. Should fail the build in this case. try { string existingCgManifest = File.ReadAllText(Configuration.FrontEnd.ValidateCgManifestForNugets.ToString(Context.PathTable)); FrontEndHost.Engine.RecordFrontEndFile( Configuration.FrontEnd.ValidateCgManifestForNugets, CGManifestResolverName); if (!NugetCgManifestGenerator.CompareForEquality(generatedCgManifest, existingCgManifest)) { Logger.ReportComponentGovernanceValidationError(Context.LoggingContext, @"Existing Component Governance Manifest file is outdated, please generate a new one using the argument /generateCgManifestForNugets:" + Configuration.FrontEnd.ValidateCgManifestForNugets.ToString(Context.PathTable)); return(false); } } // CgManifest FileNotFound, log error and fail build catch (DirectoryNotFoundException e) { Logger.ReportComponentGovernanceValidationError(Context.LoggingContext, "Cannot read Component Governance Manifest file from disk\n" + e.ToString()); return(false); } catch (FileNotFoundException e) { Logger.ReportComponentGovernanceValidationError(Context.LoggingContext, "Cannot read Component Governance Manifest file from disk\n" + e.ToString()); return(false); } return(true); }
public void TestSinglePackage() { MultiValueDictionary <string, Package> packages = new MultiValueDictionary <string, Package> { { "test.package.name", CreatePackage("1.0.1") } }; string expectedMainifest = @" { ""Version"": 1, ""Registrations"": [ { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""test.package.name"", ""Version"": ""1.0.1"" } } } ] }"; XAssert.IsTrue(NugetCgManifestGenerator.CompareForEquality(expectedMainifest, m_generator.GenerateCgManifestForPackages(packages))); }
public void TestCompareForEqualityInvalidFormat() { string validJson = "{ }"; string inValidJson = "{ "; XAssert.IsFalse(NugetCgManifestGenerator.CompareForEquality(validJson, inValidJson)); }
public void TestEmptyPackages() { MultiValueDictionary <string, Package> packages = new MultiValueDictionary <string, Package>(); var manifest = m_generator.GenerateCgManifestForPackages(packages); var cgmanifest = new { Version = 1, Registrations = new object[0] }; string expectedManifest = JsonConvert.SerializeObject(cgmanifest, Formatting.Indented); XAssert.IsTrue(NugetCgManifestGenerator.CompareForEquality(manifest, expectedManifest)); }
/// <inheritdoc/> public override async Task <bool> InitResolverAsync(IResolverSettings resolverSettings, object workspaceResolver) { Contract.Requires(resolverSettings != null); Contract.Assert(m_resolverState == State.Created); Contract.Assert( resolverSettings is INugetResolverSettings, I($"Wrong type for resolver settings, expected {nameof(INugetResolverSettings)} but got {nameof(resolverSettings.GetType)}")); Name = resolverSettings.Name; m_resolverState = State.ResolverInitializing; m_nugetWorkspaceResolver = workspaceResolver as WorkspaceNugetModuleResolver; Contract.Assert(m_nugetWorkspaceResolver != null, "Workspace module resolver is expected to be of source type"); // TODO: We could do something smarter in the future and just download/generate what is needed // Use this result to populate the dictionaries that are used for package retrieval (m_packageDirectories, m_packages and m_owningModules) var maybePackages = await m_nugetWorkspaceResolver.GetAllKnownPackagesAsync(); if (!maybePackages.Succeeded) { // Error should have been reported. return(false); } m_owningModules = new Dictionary <ModuleId, Package>(); foreach (var package in maybePackages.Result.Values.SelectMany(v => v)) { m_packages[package.Id] = package; m_owningModules[package.ModuleId] = package; } if (Configuration.FrontEnd.GenerateCgManifestForNugets.IsValid || Configuration.FrontEnd.ValidateCgManifestForNugets.IsValid) { var cgManfiestGenerator = new NugetCgManifestGenerator(Context); string generatedCgManifest = cgManfiestGenerator.GenerateCgManifestForPackages(maybePackages.Result); if (Configuration.FrontEnd.ValidateCgManifestForNugets.IsValid) { // Validate existing CG Manifest with newly generated CG Manifest if (!ValidateCgManifestFile(generatedCgManifest)) { return(false); } } if (Configuration.FrontEnd.GenerateCgManifestForNugets.IsValid && !Configuration.FrontEnd.GenerateCgManifestForNugets.Equals(Configuration.FrontEnd.ValidateCgManifestForNugets)) { // Save the generated CG Manifets to File if (!(await SaveCgManifetsFileAsync(generatedCgManifest))) { return(false); } } } m_resolverState = State.ResolverInitialized; return(true); }
public void TestCompareForEquality() { string intendedManifest = @"{ ""Version"": 1, ""Registrations"": [ { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""Antlr4.Runtime.Standard"", ""Version"": ""4.7.2"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""Aria.Cpp.SDK"", ""Version"": ""8.5.6"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""ArtifactServices.App.Shared"", ""Version"": ""17.150.28901-buildid9382555"" } } } ] } "; string noSpaceManifest = @"{ ""Version"":1,""Registrations"":[{ ""Component"":{ ""Type"":""NuGet"", ""NuGet"":{ ""Name"":""Antlr4.Runtime.Standard"", ""Version"":""4.7.2"" }}}, { ""Component"":{ ""Type"":""NuGet"", ""NuGet"":{ ""Name"":""Aria.Cpp.SDK"", ""Version"":""8.5.6"" }}}, { ""Component"":{ ""Type"":""NuGet"", ""NuGet"":{ ""Name"":""ArtifactServices.App.Shared"", ""Version"":""17.150.28901-buildid9382555"" }}}]} "; XAssert.IsTrue(NugetCgManifestGenerator.CompareForEquality(noSpaceManifest, intendedManifest)); }
public NugetCgManifestGeneratorTests() { m_context = FrontEndContext.CreateInstanceForTesting(); m_generator = new NugetCgManifestGenerator(m_context); }
public void TestSorted() { MultiValueDictionary <string, Package> packages = new MultiValueDictionary <string, Package> { { "test.package.name", CreatePackage("2.0.1") }, { "test.package.name", CreatePackage("1.0.2") }, { "test.package.a", CreatePackage("5.1.1") }, { "test.package.z", CreatePackage("1.0.0") }, { "test.package.name", CreatePackage("1.0.1") }, { "test.a.name", CreatePackage("10.0.1") }, { "DotNet.Glob", CreatePackage("1.1.1") }, { "Dotnet-Runtime", CreatePackage("1.1.1") }, }; string expectedMainifest = @" { ""Version"": 1, ""Registrations"": [ { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""DotNet.Glob"", ""Version"": ""1.1.1"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""Dotnet-Runtime"", ""Version"": ""1.1.1"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""test.a.name"", ""Version"": ""10.0.1"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""test.package.a"", ""Version"": ""5.1.1"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""test.package.name"", ""Version"": ""1.0.1"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""test.package.name"", ""Version"": ""1.0.2"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""test.package.name"", ""Version"": ""2.0.1"" } } }, { ""Component"": { ""Type"": ""NuGet"", ""NuGet"": { ""Name"": ""test.package.z"", ""Version"": ""1.0.0"" } } } ] }"; var generated = m_generator.GenerateCgManifestForPackages(packages); XAssert.IsTrue(NugetCgManifestGenerator.CompareForEquality(expectedMainifest, generated), "Actual: " + generated); }
public override async Task <bool> InitResolverAsync(IResolverSettings resolverSettings, object workspaceResolver) { Contract.Requires(resolverSettings != null); Contract.Assert(m_resolverState == State.Created); Contract.Assert( resolverSettings is INugetResolverSettings, I($"Wrong type for resolver settings, expected {nameof(INugetResolverSettings)} but got {nameof(resolverSettings.GetType)}")); Name = resolverSettings.Name; m_resolverState = State.ResolverInitializing; m_nugetWorkspaceResolver = workspaceResolver as WorkspaceNugetModuleResolver; Contract.Assert(m_nugetWorkspaceResolver != null, "Workspace module resolver is expected to be of source type"); // TODO: We could do something smarter in the future and just download/generate what is needed // Use this result to populate the dictionaries that are used for package retrieval (m_packageDirectories, m_packages and m_owningModules) var maybePackages = await m_nugetWorkspaceResolver.GetAllKnownPackagesAsync(); if (!maybePackages.Succeeded) { // Error should have been reported. return(false); } m_owningModules = new Dictionary <ModuleId, Package>(); foreach (var package in maybePackages.Result.Values.SelectMany(v => v)) { m_packages[package.Id] = package; m_owningModules[package.ModuleId] = package; } if (Configuration.FrontEnd.GenerateCgManifestForNugets.IsValid || Configuration.FrontEnd.ValidateCgManifestForNugets.IsValid) { var cgManfiestGenerator = new NugetCgManifestGenerator(Context); string generatedCgManifest = cgManfiestGenerator.GenerateCgManifestForPackages(maybePackages.Result); string existingCgManifest = "INVALID"; if (!Configuration.FrontEnd.GenerateCgManifestForNugets.IsValid && Configuration.FrontEnd.ValidateCgManifestForNugets.IsValid) { // Validation of existing cgmainfest.json results in failure due to mismatch. Should fail the build in this case. try { existingCgManifest = File.ReadAllText(Configuration.FrontEnd.ValidateCgManifestForNugets.ToString(Context.PathTable)); FrontEndHost.Engine.RecordFrontEndFile( Configuration.FrontEnd.ValidateCgManifestForNugets, CGManifestResolverName); } // CgManifest FileNotFound, log error and fail build catch (DirectoryNotFoundException e) { Logger.ReportComponentGovernanceValidationError(Context.LoggingContext, "Cannot read Component Governance Manifest file from disk\n" + e.ToString()); return(false); } catch (FileNotFoundException e) { Logger.ReportComponentGovernanceValidationError(Context.LoggingContext, "Cannot read Component Governance Manifest file from disk\n" + e.ToString()); return(false); } if (!cgManfiestGenerator.CompareForEquality(generatedCgManifest, existingCgManifest)) { Logger.ReportComponentGovernanceValidationError(Context.LoggingContext, @"Existing Component Governance Manifest file is outdated, please generate a new one using the argument /generateCgManifestForNugets:<path>"); return(false); } m_resolverState = State.ResolverInitialized; return(true); } // GenerateCgManifestForNugets writes a new file when the old file does not match, hence it will always be valid and does not need validation try { // We are calling FrontEndHost.Engine.RecordFrontEndFile towards the end of this function because we may update this file after the read below // Updating the file will cause a hash mismatch and the build to fail if this file is read again downstream existingCgManifest = File.ReadAllText(Configuration.FrontEnd.GenerateCgManifestForNugets.ToString(Context.PathTable)); } // CgManifest FileNotFound, continue to write the new file // No operations required as the empty existingCgManifest will not match with the newly generated cgManifest catch (DirectoryNotFoundException) { } catch (FileNotFoundException) { } if (!cgManfiestGenerator.CompareForEquality(generatedCgManifest, existingCgManifest)) { if (Configuration.FrontEnd.GenerateCgManifestForNugets.IsValid) { // Overwrite or create new cgmanifest.json file with updated nuget package and version info string targetFilePath = Configuration.FrontEnd.GenerateCgManifestForNugets.ToString(Context.PathTable); try { FileUtilities.CreateDirectory(Path.GetDirectoryName(targetFilePath)); await FileUtilities.WriteAllTextAsync(targetFilePath, generatedCgManifest, Encoding.UTF8); } catch (BuildXLException e) { Logger.ReportComponentGovernanceGenerationError(Context.LoggingContext, "Could not write Component Governance Manifest file to disk\n" + e.ToString()); return(false); } } } FrontEndHost.Engine.RecordFrontEndFile( Configuration.FrontEnd.GenerateCgManifestForNugets, CGManifestResolverName); } m_resolverState = State.ResolverInitialized; return(true); }