Exemple #1
0
        public async Task DotnetTrust_AuthorAction_RelativePathConfileFile_Succeeds(bool allowUntrustedRoot)
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var package             = new SimpleTestPackageContext();

            using (SimpleTestPathContext pathContext = _msbuildFixture.CreateSimpleTestPathContext())
                using (MemoryStream zipStream = await package.CreateAsStreamAsync())
                    using (TrustedTestCert <TestCertificate> trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        string certFingerprint   = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        string signedPackagePath = await SignedArchiveTestUtility.AuthorSignPackageAsync(trustedTestCert.Source.Cert, package, pathContext.PackageSource);

                        var config = $@"<?xml version=""1.0"" encoding=""utf-8""?>
                    <configuration>
                      <packageSources>
                        <!--To inherit the global NuGet package sources remove the <clear/> line below -->
                        <clear />
                        <add key=""NuGetSource"" value=""{pathContext.PackageSource}"" />
                       </packageSources>
                      <config>
                        <add key=""signaturevalidationmode"" value=""accept"" />
                      </config>
                      <trustedSigners>
                      </trustedSigners>
                    </configuration>";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, pathContext.WorkingDirectory, config);
                        var nugetConfigPath          = Path.Combine(pathContext.WorkingDirectory, nugetConfigFileName);
                        var allowUntrustedRootArg    = allowUntrustedRoot ? "--allow-untrusted-root" : string.Empty;
                        var allowUntruestedRootValue = allowUntrustedRoot ? "true" : "false";

                        // Act
                        CommandRunnerResult resultAdd = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust author nuget {signedPackagePath}  {allowUntrustedRootArg} --configfile ..{Path.DirectorySeparatorChar}{nugetConfigFileName}");

                        // Assert
                        resultAdd.Success.Should().BeTrue();
                        resultAdd.AllOutput.Should().Contain(string.Format(CultureInfo.CurrentCulture, _successfulAddTrustedSigner, "author", "nuget"));

                        string expectedResult = SettingsTestUtils.RemoveWhitespace($@"<?xml version=""1.0"" encoding=""utf-8""?>
                    <configuration>
                      <packageSources>
                        <!--To inherit the global NuGet package sources remove the < clear /> line below-->
                        <clear/>
                        <add key = ""NuGetSource"" value = ""{pathContext.PackageSource}""/>
                       </packageSources >
                      <config>
                        <add key = ""signaturevalidationmode"" value = ""accept""/>
                      </config>
                      < trustedSigners>
                            <author name = ""nuget"">
                                 <certificate fingerprint = ""{certFingerprint}"" hashAlgorithm = ""SHA256"" allowUntrustedRoot = ""{allowUntruestedRootValue}""/>
                            </author>
                      </trustedSigners>
                    </configuration>");

                        SettingsTestUtils.RemoveWhitespace(File.ReadAllText(nugetConfigPath)).Should().Be(expectedResult);
                    }
        }
Exemple #2
0
        public async Task GetTrustResultAsync_VerifyWithCertificateInAllowList_Success()
        {
            // Arrange
            var nupkg = new SimpleTestPackageContext();

            using (var dir = TestDirectory.Create())
                using (var testCertificate = new X509Certificate2(_trustedTestCert.Source.Cert))
                {
                    var certificateFingerprintString = SignatureTestUtility.GetFingerprint(testCertificate, HashAlgorithmName.SHA256);

                    var signedPackagePath = await SignedArchiveTestUtility.AuthorSignPackageAsync(testCertificate, nupkg, dir);

                    var allowListHashes = new[] { certificateFingerprintString, "abc" };
                    var allowList       = allowListHashes.Select(hash => new CertificateHashAllowListEntry(VerificationTarget.Primary, hash)).ToList();

                    var trustProviders = new[]
                    {
                        new AllowListVerificationProvider(allowList)
                    };

                    var verifier = new PackageSignatureVerifier(trustProviders, _settings);

                    using (var packageReader = new PackageArchiveReader(signedPackagePath))
                    {
                        // Act
                        var result = await verifier.VerifySignaturesAsync(packageReader, CancellationToken.None);

                        // Assert
                        result.Valid.Should().BeTrue();
                    }
                }
        }
        public async Task TrustedSignersCommand_AddTrustedSigner_WithRepositoryCountersignedPackage_AddsItSuccesfullyToConfigAsync(bool allowUntrustedRoot, string owners)
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var config = @"<?xml version=""1.0"" encoding=""utf-8""?>
<configuration>
</configuration>";

            // Arrange
            var package = new SimpleTestPackageContext();

            using (var dir = TestDirectory.Create())
                using (var zipStream = await package.CreateAsStreamAsync())
                    using (var authorTrustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                        using (var repoTrustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                        {
                            var certFingerprint         = SignatureTestUtility.GetFingerprint(repoTrustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                            var repoServiceIndex        = "https://serviceindex.test/v3/index.json";
                            var authorSignedPackagePath = await SignedArchiveTestUtility.AuthorSignPackageAsync(authorTrustedTestCert.Source.Cert, package, dir);

                            var signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(repoTrustedTestCert.Source.Cert, authorSignedPackagePath, dir, new Uri(repoServiceIndex));

                            SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, dir, config);
                            var nugetConfigPath       = Path.Combine(dir, nugetConfigFileName);
                            var allowUntrustedRootArg = allowUntrustedRoot ? "-AllowUntrustedRoot" : string.Empty;
                            var ownersArgs            = string.Empty;
                            var expectedOwners        = string.Empty;

                            if (owners != null)
                            {
                                ownersArgs     = $"-Owners {owners}";
                                expectedOwners = $"<owners>{owners}</owners>";
                            }

                            // Act
                            var commandResult = CommandRunner.Run(
                                _nugetExePath,
                                dir,
                                $"trusted-signers add {signedPackagePath} -Name signer -Repository {allowUntrustedRootArg} {ownersArgs} -Config {nugetConfigPath}",
                                waitForExit: true);

                            // Assert
                            commandResult.Success.Should().BeTrue();
                            commandResult.AllOutput.Should().Contain(string.Format(CultureInfo.CurrentCulture, _successfulAddTrustedSigner, "repository", "signer"));

                            var expectedResult = SettingsTestUtils.RemoveWhitespace($@"<?xml version=""1.0"" encoding=""utf-8""?>
<configuration>
<trustedSigners>
    <repository name=""signer"" serviceIndex=""{repoServiceIndex}"">
        <certificate fingerprint=""{certFingerprint}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot.ToString().ToLower()}"" />
        {expectedOwners}
    </repository>
</trustedSigners>
</configuration>");

                            SettingsTestUtils.RemoveWhitespace(File.ReadAllText(nugetConfigPath)).Should().Be(expectedResult);
                        }
        }
        public async Task ClientPolicies_WithoutSignerInTrustedSignersList_WithMatchingOwnersAsync(SigningTestType signature, string validationMode, bool expectedResult, int expectedErrors, int expectedWarnings)
        {
            // Arrange
            using (var dir = TestDirectory.Create())
                using (var authorCertificate = new X509Certificate2(_trustedAuthorTestCert.Source.Cert))
                    using (var repoCertificate = new X509Certificate2(_trustedRepoTestCert.Source.Cert))
                    {
                        var authorCertificateFingerprintString = SignatureTestUtility.GetFingerprint(authorCertificate, HashAlgorithmName.SHA256);
                        var repoCertificateFingerprintString   = SignatureTestUtility.GetFingerprint(repoCertificate, HashAlgorithmName.SHA256);

                        var signedPackagePath = await CreateSignedPackageAsync(dir, signature, authorCertificate, repoCertificate);

                        var config = $@"
<configuration>
    <config>
        <add key=""signatureValidationMode"" value=""{validationMode}"" />
    </config>
    <trustedSigners>
        <repository name=""repo1"" serviceIndex=""https://api.v3serviceIndex.test/json"">
            <certificate fingerprint=""abc"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""false"" />
            <owners>owner1</owners>
        </repository>
    </trustedSigners>
</configuration>";

                        var nugetConfigPath = "NuGet.Config";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigPath, dir, config);

                        // Act and Assert
                        var settings = new Settings(dir);

                        var verifierSettings = SignedPackageVerifierSettings.GetClientPolicy(settings, NullLogger.Instance);
                        var trustProviders   = new[]
                        {
                            new AllowListVerificationProvider()
                        };
                        var verifier = new PackageSignatureVerifier(trustProviders);

                        using (var packageReader = new PackageArchiveReader(signedPackagePath))
                        {
                            // Act
                            var result = await verifier.VerifySignaturesAsync(packageReader, verifierSettings, CancellationToken.None);

                            var resultsWithWarnings = result.Results.Where(r => r.GetWarningIssues().Any());
                            var resultsWithErrors   = result.Results.Where(r => r.GetErrorIssues().Any());
                            var totalWarningIssues  = resultsWithWarnings.SelectMany(r => r.GetWarningIssues());
                            var totalErrorIssues    = resultsWithErrors.SelectMany(r => r.GetErrorIssues());

                            // Assert
                            result.Valid.Should().Be(expectedResult);
                            totalWarningIssues.Count().Should().Be(expectedWarnings);
                            totalErrorIssues.Count().Should().Be(expectedErrors);
                        }
                    }
        }
Exemple #5
0
        public async Task DotnetTrust_CertificateFingerPrintAction_WithExistingSigner_AppendSucceeds(bool allowUntrustedRoot)
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var package             = new SimpleTestPackageContext();

            using (SimpleTestPathContext pathContext = _msbuildFixture.CreateSimpleTestPathContext())
                using (MemoryStream zipStream = await package.CreateAsStreamAsync())
                    using (TrustedTestCert <TestCertificate> trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        var certFingerprint   = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        var repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                        var signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(trustedTestCert.Source.Cert, package, pathContext.PackageSource, new Uri(repoServiceIndex));

                        var config = @"<?xml version=""1.0"" encoding=""utf-8""?>
<configuration>
    <trustedSigners>
        <author name=""MyCompanyCert"">
            <certificate fingerprint=""abcdefg"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""false"" />
        </author>
    </trustedSigners>
</configuration>";

                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, pathContext.WorkingDirectory, config);
                        var nugetConfigPath          = Path.Combine(pathContext.WorkingDirectory, nugetConfigFileName);
                        var allowUntrustedRootArg    = allowUntrustedRoot ? "--allow-untrusted-root" : string.Empty;
                        var allowUntruestedRootValue = allowUntrustedRoot ? "true" : "false";
                        var authorName = "MyCompanyCert";

                        // Act
                        CommandRunnerResult resultAdd = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust certificate {authorName} {certFingerprint} {allowUntrustedRootArg}  --algorithm SHA256 --configfile {nugetConfigPath}");

                        // Assert
                        resultAdd.Success.Should().BeTrue();
                        resultAdd.AllOutput.Should().Contain(string.Format(CultureInfo.CurrentCulture, "Successfully updated the trusted signer '{0}'.", authorName));

                        string expectedResult = SettingsTestUtils.RemoveWhitespace($@"<?xml version=""1.0"" encoding=""utf-8""?>
                <configuration>
                    < trustedSigners>
                        <author name = ""{authorName}"">
                                < certificate fingerprint = ""abcdefg"" hashAlgorithm = ""SHA256"" allowUntrustedRoot = ""false""/>
                                < certificate fingerprint = ""{certFingerprint}"" hashAlgorithm = ""SHA256"" allowUntrustedRoot = ""{allowUntruestedRootValue}""/>
                        </author>
                    </trustedSigners>
                </configuration>");

                        SettingsTestUtils.RemoveWhitespace(File.ReadAllText(nugetConfigPath)).Should().Be(expectedResult);
                    }
        }
Exemple #6
0
        public async Task DotnetTrust_RepositoryAction_Succeeds(bool allowUntrustedRoot, string owners)
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var package             = new SimpleTestPackageContext();

            using (SimpleTestPathContext pathContext = _msbuildFixture.CreateSimpleTestPathContext())
                using (MemoryStream zipStream = await package.CreateAsStreamAsync())
                    using (TrustedTestCert <TestCertificate> trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        var certFingerprint   = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        var repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                        var signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(trustedTestCert.Source.Cert, package, pathContext.PackageSource, new Uri(repoServiceIndex));

                        var config = $@"<?xml version=""1.0"" encoding=""utf-8""?>
                <configuration>
                </configuration>";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, pathContext.WorkingDirectory, config);
                        var nugetConfigPath          = Path.Combine(pathContext.WorkingDirectory, nugetConfigFileName);
                        var allowUntrustedRootArg    = allowUntrustedRoot ? "--allow-untrusted-root" : string.Empty;
                        var allowUntruestedRootValue = allowUntrustedRoot ? "true" : "false";
                        var ownersArgs     = string.Empty;
                        var expectedOwners = string.Empty;

                        if (owners != null)
                        {
                            ownersArgs     = $"--owners {owners}";
                            expectedOwners = $"<owners>{owners}</owners>";
                        }

                        // Act
                        CommandRunnerResult resultAdd = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust repository nuget {signedPackagePath}  {allowUntrustedRootArg} {ownersArgs} --configfile {nugetConfigPath}");

                        // Assert
                        resultAdd.Success.Should().BeTrue();
                        resultAdd.AllOutput.Should().Contain(string.Format(CultureInfo.CurrentCulture, _successfulAddTrustedSigner, "repository", "nuget"));

                        string expectedResult = SettingsTestUtils.RemoveWhitespace($@"<?xml version=""1.0"" encoding=""utf-8""?>
                <configuration>
                    < trustedSigners>
                        <repository name = ""nuget"" serviceIndex=""https://serviceindex.test/v3/index.json"">
                                < certificate fingerprint = ""{certFingerprint}"" hashAlgorithm = ""SHA256"" allowUntrustedRoot = ""{allowUntruestedRootValue}""/>{expectedOwners}
                        </repository>
                    </trustedSigners>
                </configuration>");

                        SettingsTestUtils.RemoveWhitespace(File.ReadAllText(nugetConfigPath)).Should().Be(expectedResult);
                    }
        }
Exemple #7
0
        public async Task Verify_RepositorySignedPackage_WithAuthorItemUntrustedCertificate_Fails(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            IX509StoreCertificate storeCertificate = _signFixture.UntrustedSelfIssuedCertificateInCertificateStore;

            // Arrange
            using (var pathContext = new SimpleTestPathContext())
            {
                var    nupkg         = new SimpleTestPackageContext("A", "1.0.0");
                string testDirectory = pathContext.WorkingDirectory;
                await SimpleTestPackageUtility.CreatePackagesAsync(testDirectory, nupkg);

                string packagePath = Path.Combine(testDirectory, nupkg.PackageName);

                //Act
                string certificateFingerprintString = SignatureTestUtility.GetFingerprint(storeCertificate.Certificate, HashAlgorithmName.SHA256);
                string repoServiceIndex             = "https://serviceindex.test/v3/index.json";
                string signedPackagePath            = await SignedArchiveTestUtility.RepositorySignPackageAsync(storeCertificate.Certificate, packagePath, pathContext.PackageSource, new Uri(repoServiceIndex));

                // Arrange
                string trustedSignersSectionContent = $@"
    <trustedSigners>
        <author name=""MyCert"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
        </author>
    </trustedSigners>
";
                SimpleTestSettingsContext.AddSectionIntoNuGetConfig(pathContext.WorkingDirectory, trustedSignersSectionContent, "configuration");
                string fingerprint = verifyCertificateFingerprint ? $"--certificate-fingerprint {certificateFingerprintString} --certificate-fingerprint def" : string.Empty;

                //Act
                CommandRunnerResult verifyResult = _msbuildFixture.RunDotnet(
                    testDirectory,
                    $"nuget verify {signedPackagePath} {fingerprint}",
                    ignoreExitCode: true);

                // Assert
                verifyResult.Success.Should().BeFalse(because: verifyResult.AllOutput);
                verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
                verifyResult.AllOutput.Should().Contain(_noMatchingCertErrorCode);
                verifyResult.AllOutput.Should().Contain("This package is signed but not by a trusted signer.");

                if (bool.TryParse(allowUntrustedRoot, out bool parsed) && !parsed)
                {
                    verifyResult.AllOutput.Should().Contain(_primarySignatureInvalidErrorCode);
                }
                else
                {
                    verifyResult.AllOutput.Should().NotContain(_primarySignatureInvalidErrorCode);
                }
            }
        }
Exemple #8
0
        public async Task Verify_RepositorySignedPackage_WithRepositoryItemTrustedCertificate_AllowUntrustedRootSet_CorrectOwners_Succeeds(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            // Arrange
            IX509StoreCertificate storeCertificate = _signFixture.DefaultCertificate;

            using (var pathContext = new SimpleTestPathContext())
            {
                var    package         = new SimpleTestPackageContext();
                string certFingerprint = SignatureTestUtility.GetFingerprint(storeCertificate.Certificate, HashAlgorithmName.SHA256);
                var    packageOwners   = new List <string>()
                {
                    "nuget",
                    "contoso"
                };
                string repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                string signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(
                    storeCertificate.Certificate,
                    package,
                    pathContext.PackageSource,
                    new Uri(repoServiceIndex),
                    timestampService : null,
                    packageOwners);

                string testDirectory = pathContext.WorkingDirectory;

                string trustedSignersSectionContent = $@"
    <trustedSigners>
    <repository name=""NuGetTrust"" serviceIndex=""{repoServiceIndex}"">
      <certificate fingerprint=""{certFingerprint}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
      <owners>nuget;Contoso</owners>
    </repository>
    </trustedSigners>
";
                SimpleTestSettingsContext.AddSectionIntoNuGetConfig(testDirectory, trustedSignersSectionContent, "configuration");
                string fingerprint = verifyCertificateFingerprint ? $"--certificate-fingerprint {certFingerprint} --certificate-fingerprint DEF" : string.Empty;

                //Act
                CommandRunnerResult verifyResult = _msbuildFixture.RunDotnet(
                    testDirectory,
                    $"nuget verify {signedPackagePath} {fingerprint}",
                    ignoreExitCode: true);

                // Assert
                // For certificate with trusted root setting allowUntrustedRoot value true/false doesn't matter.
                // Owners is casesensitive, here owner "nuget" matches
                verifyResult.Success.Should().BeTrue();
                verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
            }
        }
        public async Task ClientPolicies_WithNoTrustedSignersListAsync(SigningTestType signature, string validationMode, bool expectedResult, int expectedErrors)
        {
            // Arrange
            using (var dir = TestDirectory.Create())
                using (var authorCertificate = new X509Certificate2(_trustedAuthorTestCert.Source.Cert))
                    using (var repoCertificate = new X509Certificate2(_trustedRepoTestCert.Source.Cert))
                    {
                        var authorCertificateFingerprintString = SignatureTestUtility.GetFingerprint(authorCertificate, HashAlgorithmName.SHA256);
                        var repoCertificateFingerprintString   = SignatureTestUtility.GetFingerprint(repoCertificate, HashAlgorithmName.SHA256);
                        var signedPackagePath = await CreateSignedPackageAsync(dir, signature, authorCertificate, repoCertificate);

                        var config = $@"
<configuration>
    <config>
        <add key=""signatureValidationMode"" value=""{validationMode}"" />
    </config>
</configuration>";

                        var nugetConfigPath = "NuGet.Config";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigPath, dir, config);

                        // Act and Assert
                        var settings = new Settings(dir);

                        var clientPolicyContext = ClientPolicyContext.GetClientPolicy(settings, NullLogger.Instance);
                        var trustProviders      = new[]
                        {
                            new AllowListVerificationProvider(clientPolicyContext.AllowList, requireNonEmptyAllowList: clientPolicyContext.Policy == SignatureValidationMode.Require)
                        };
                        var verifier = new PackageSignatureVerifier(trustProviders);

                        using (var packageReader = new PackageArchiveReader(signedPackagePath))
                        {
                            // Act
                            var result = await verifier.VerifySignaturesAsync(packageReader, clientPolicyContext.VerifierSettings, CancellationToken.None);

                            var resultsWithWarnings = result.Results.Where(r => r.GetWarningIssues().Any());
                            var resultsWithErrors   = result.Results.Where(r => r.GetErrorIssues().Any());
                            var totalWarningIssues  = resultsWithWarnings.SelectMany(r => r.GetWarningIssues());
                            var totalErrorIssues    = resultsWithErrors.SelectMany(r => r.GetErrorIssues());

                            // Assert
                            result.IsValid.Should().Be(expectedResult);
                            totalWarningIssues.Count().Should().Be(0);
                            totalErrorIssues.Count().Should().Be(expectedErrors);
                        }
                    }
        }
Exemple #10
0
        public async Task Verify_RepositorySignedPackage_WithRepositoryItemUntrustedCertificate_AllowUntrustedRootSetTrue_WrongOwners_Fails(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            IX509StoreCertificate storeCertificate = _signFixture.UntrustedSelfIssuedCertificateInCertificateStore;

            // Arrange
            using (var pathContext = new SimpleTestPathContext())
            {
                var nupkg = new SimpleTestPackageContext("A", "1.0.0");
                await SimpleTestPackageUtility.CreatePackagesAsync(pathContext.WorkingDirectory, nupkg);

                string packagePath = Path.Combine(pathContext.WorkingDirectory, nupkg.PackageName);

                //Act
                var certificateFingerprintString = SignatureTestUtility.GetFingerprint(storeCertificate.Certificate, HashAlgorithmName.SHA256);
                var packageOwners = new List <string>()
                {
                    "nuget",
                    "contoso"
                };
                string repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                string signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(storeCertificate.Certificate, packagePath, pathContext.PackageSource, new Uri(repoServiceIndex), null, packageOwners);

                // Arrange
                string trustedSignersSectionContent = $@"
    <trustedSigners>
        <repository name=""MyCert"" serviceIndex = ""{repoServiceIndex}"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
            <owners>Nuget;Contoso</owners>
        </repository>
    </trustedSigners>
";
                SimpleTestSettingsContext.AddSectionIntoNuGetConfig(pathContext.WorkingDirectory, trustedSignersSectionContent, "configuration");
                string fingerprint = verifyCertificateFingerprint ? $"--certificate-fingerprint {certificateFingerprintString} --certificate-fingerprint DEF" : string.Empty;

                //Act
                CommandRunnerResult verifyResult = _msbuildFixture.RunDotnet(
                    pathContext.WorkingDirectory,
                    $"nuget verify {signedPackagePath} {fingerprint}",
                    ignoreExitCode: true);

                // Assert
                // Owners is casesensitive, owner info should be "nuget;contoso" not "Nuget;Contoso"
                verifyResult.Success.Should().BeFalse(because: verifyResult.AllOutput);
                verifyResult.AllOutput.Should().Contain(_noMatchingCertErrorCode);
                verifyResult.AllOutput.Should().Contain("This package is signed but not by a trusted signer.");
            }
        }
Exemple #11
0
        public async Task Verify_RepositorySignedPackage_WithRepositoryItemUntrustedCertificate_AllowUntrustedRootSetTrue_CorrectOwners_Succeeds(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            // Arrange
            using (var pathContext = new SimpleTestPathContext())
                using (var testCertificate = new X509Certificate2(_testFixture.UntrustedSelfIssuedCertificateInCertificateStore))
                {
                    var nupkg = new SimpleTestPackageContext("A", "1.0.0");
                    await SimpleTestPackageUtility.CreatePackagesAsync(pathContext.WorkingDirectory, nupkg);

                    string packagePath = Path.Combine(pathContext.WorkingDirectory, nupkg.PackageName);

                    //Act
                    string certificateFingerprintString = SignatureTestUtility.GetFingerprint(testCertificate, HashAlgorithmName.SHA256);
                    var    packageOwners = new List <string>()
                    {
                        "nuget",
                        "contoso"
                    };
                    string repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                    string signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(testCertificate, packagePath, pathContext.PackageSource, new Uri(repoServiceIndex), null, packageOwners);

                    // Arrange
                    string trustedSignersSectionContent = $@"
    <trustedSigners>
        <repository name=""MyCert"" serviceIndex = ""{repoServiceIndex}"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
            <owners>nuget;Contoso</owners>
        </repository>
    </trustedSigners>
";
                    SimpleTestSettingsContext.AddSectionIntoNuGetConfig(pathContext.WorkingDirectory, trustedSignersSectionContent, "configuration");
                    string fingerprint = verifyCertificateFingerprint ? $"-CertificateFingerprint {certificateFingerprintString};def" : string.Empty;

                    // Act
                    CommandRunnerResult verifyResult = CommandRunner.Run(
                        _nugetExePath,
                        pathContext.PackageSource,
                        $"verify {signedPackagePath} -Signatures {fingerprint}",
                        waitForExit: true);

                    // Assert
                    // Owners is casesensitive, here owner "nuget" matches
                    verifyResult.Success.Should().BeTrue();
                    verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
                }
        }
        public async Task GetSigningCertificateFingerprint_SuccessfullyHashesMultipleAlgorithms()
        {
            using (var test = await VerifyTest.CreateAsync(settings: null, certificate: _untrustedTestCertificate.Cert))
            {
                var sha256 = test.PrimarySignature.GetSigningCertificateFingerprint(HashAlgorithmName.SHA256);
                var sha384 = test.PrimarySignature.GetSigningCertificateFingerprint(HashAlgorithmName.SHA384);
                var sha512 = test.PrimarySignature.GetSigningCertificateFingerprint(HashAlgorithmName.SHA512);

                var expectedSha256 = SignatureTestUtility.GetFingerprint(_untrustedTestCertificate.Cert, HashAlgorithmName.SHA256);
                var expectedSha384 = SignatureTestUtility.GetFingerprint(_untrustedTestCertificate.Cert, HashAlgorithmName.SHA384);
                var expectedSha512 = SignatureTestUtility.GetFingerprint(_untrustedTestCertificate.Cert, HashAlgorithmName.SHA512);

                Assert.Equal(sha256, expectedSha256, StringComparer.Ordinal);
                Assert.Equal(sha384, expectedSha384, StringComparer.Ordinal);
                Assert.Equal(sha512, expectedSha512, StringComparer.Ordinal);
            }
        }
        public async Task TrustedSignersCommand_AddTrustedSigner_WithAuthorSignedPackage_AddsItSuccesfullyToConfigAsync(bool allowUntrustedRoot)
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var config = @"<?xml version=""1.0"" encoding=""utf-8""?>
<configuration>
</configuration>";

            // Arrange
            var package = new SimpleTestPackageContext();

            using (var dir = TestDirectory.Create())
                using (var zipStream = await package.CreateAsStreamAsync())
                    using (var trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        var certFingerprint   = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        var signedPackagePath = await SignedArchiveTestUtility.AuthorSignPackageAsync(trustedTestCert.Source.Cert, package, dir);

                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, dir, config);
                        var nugetConfigPath       = Path.Combine(dir, nugetConfigFileName);
                        var allowUntrustedRootArg = allowUntrustedRoot ? "-AllowUntrustedRoot" : string.Empty;

                        // Act
                        var commandResult = CommandRunner.Run(
                            _nugetExePath,
                            dir,
                            $"trusted-signers add {signedPackagePath} -Name signer -Author {allowUntrustedRootArg} -Config {nugetConfigPath}",
                            waitForExit: true);

                        // Assert
                        commandResult.Success.Should().BeTrue();
                        commandResult.AllOutput.Should().Contain(string.Format(CultureInfo.CurrentCulture, _successfulAddTrustedSigner, "author", "signer"));

                        var expectedResult = SettingsTestUtils.RemoveWhitespace($@"<?xml version=""1.0"" encoding=""utf-8""?>
<configuration>
<trustedSigners>
    <author name=""signer"">
        <certificate fingerprint=""{certFingerprint}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot.ToString().ToLower()}"" />
    </author>
</trustedSigners>
</configuration>");

                        SettingsTestUtils.RemoveWhitespace(File.ReadAllText(nugetConfigPath)).Should().Be(expectedResult);
                    }
        }
Exemple #14
0
        public async Task Verify_RepositorySignedPackage_WithRepositoryItemTrustedCertificate_AllowUntrustedRootSet_WrongOwners_Fails(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            // Arrange
            TrustedTestCert <TestCertificate> cert = _testFixture.TrustedTestCertificateChain.Leaf;

            using (var pathContext = new SimpleTestPathContext())
            {
                var    package         = new SimpleTestPackageContext();
                string certFingerprint = SignatureTestUtility.GetFingerprint(cert.Source.Cert, HashAlgorithmName.SHA256);
                var    packageOwners   = new List <string>()
                {
                    "nuget",
                    "contoso"
                };
                string repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                string signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(cert.Source.Cert, package, pathContext.PackageSource, new Uri(repoServiceIndex), null, packageOwners);

                string testDirectory = pathContext.WorkingDirectory;

                // Arrange
                string trustedSignersSectionContent = $@"
    <trustedSigners>
    <repository name=""NuGetTrust"" serviceIndex=""{repoServiceIndex}"">
      <certificate fingerprint=""{certFingerprint}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
      <owners>Nuget;Contoso</owners>
    </repository>
    </trustedSigners>
";
                SimpleTestSettingsContext.AddSectionIntoNuGetConfig(testDirectory, trustedSignersSectionContent, "configuration");
                string fingerprint = verifyCertificateFingerprint ? $"-CertificateFingerprint {certFingerprint};def" : string.Empty;

                //Act
                CommandRunnerResult verifyResult = CommandRunner.Run(
                    _nugetExePath,
                    pathContext.PackageSource,
                    $"verify {signedPackagePath} -Signatures {fingerprint}",
                    waitForExit: true);

                // Assert
                // Owners is casesensitive, owner info should be "nuget;contoso" not "Nuget;Contoso"
                verifyResult.Success.Should().BeFalse();
                verifyResult.AllOutput.Should().Contain(_noMatchingCertErrorCode);
            }
        }
Exemple #15
0
        public async Task Verify_RepositorySignedPackage_WithRepositoryItemUntrustedCertificate_AllowUntrustedRootSetFalse_Fails(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            // Arrange
            using (var pathContext = new SimpleTestPathContext())
                using (var testCertificate = new X509Certificate2(_testFixture.UntrustedSelfIssuedCertificateInCertificateStore))
                {
                    var    nupkg         = new SimpleTestPackageContext("A", "1.0.0");
                    string testDirectory = pathContext.WorkingDirectory;
                    await SimpleTestPackageUtility.CreatePackagesAsync(testDirectory, nupkg);

                    string packagePath = Path.Combine(testDirectory, nupkg.PackageName);

                    //Act
                    string certificateFingerprintString = SignatureTestUtility.GetFingerprint(testCertificate, HashAlgorithmName.SHA256);
                    string repoServiceIndex             = "https://serviceindex.test/v3/index.json";
                    string signedPackagePath            = await SignedArchiveTestUtility.RepositorySignPackageAsync(testCertificate, packagePath, pathContext.PackageSource, new Uri(repoServiceIndex));

                    // Arrange
                    string trustedSignersSectionContent = $@"
    <trustedSigners>
        <repository name=""MyCert"" serviceIndex = ""{repoServiceIndex}"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
        </repository>
    </trustedSigners>
";
                    SimpleTestSettingsContext.AddSectionIntoNuGetConfig(pathContext.WorkingDirectory, trustedSignersSectionContent, "configuration");
                    string fingerprint = verifyCertificateFingerprint ? $"-CertificateFingerprint {certificateFingerprintString};def" : string.Empty;

                    // Act
                    CommandRunnerResult verifyResult = CommandRunner.Run(
                        _nugetExePath,
                        pathContext.PackageSource,
                        $"verify {signedPackagePath} -Signatures {fingerprint}",
                        waitForExit: true);

                    // Assert
                    // Unless allowUntrustedRoot is set true in nuget.config verify always fails for cert without trusted root.
                    verifyResult.Success.Should().BeFalse(because: verifyResult.AllOutput);
                    verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
                    verifyResult.AllOutput.Should().Contain(_primarySignatureInvalidErrorCode);
                    verifyResult.AllOutput.Should().Contain("The repository primary signature's signing certificate is not trusted by the trust provider.");
                }
        }
Exemple #16
0
        public async Task DotnetTrust_RemoveAction_Succeeds()
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var package             = new SimpleTestPackageContext();

            using (SimpleTestPathContext pathContext = _msbuildFixture.CreateSimpleTestPathContext())
                using (MemoryStream zipStream = await package.CreateAsStreamAsync())
                    using (TrustedTestCert <TestCertificate> trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        var certFingerprint   = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        var repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                        var signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(trustedTestCert.Source.Cert, package, pathContext.PackageSource, new Uri(repoServiceIndex));

                        var repositoryName = "nuget";

                        var config = $@"<?xml version=""1.0"" encoding=""utf-8""?>
                <configuration>
                    <trustedSigners>
                        <repository name = ""{repositoryName}"" serviceIndex=""https://serviceindex.test/v3/index.json"">
                            <certificate fingerprint=""abcdef"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""false""/>
                        </repository>
                    </trustedSigners>
                </configuration>";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, pathContext.WorkingDirectory, config);
                        var nugetConfigPath = Path.Combine(pathContext.WorkingDirectory, nugetConfigFileName);

                        // Act
                        CommandRunnerResult resultSync = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust remove {repositoryName} --configfile {nugetConfigPath}");

                        // Assert
                        resultSync.Success.Should().BeTrue();
                        resultSync.AllOutput.Should().Contain(string.Format(CultureInfo.CurrentCulture, _successfulRemoveTrustedSigner, repositoryName));

                        string expectedResult = SettingsTestUtils.RemoveWhitespace($@"<?xml version=""1.0"" encoding=""utf-8""?>
                <configuration>
                </configuration>");

                        SettingsTestUtils.RemoveWhitespace(File.ReadAllText(nugetConfigPath)).Should().Be(expectedResult);
                    }
        }
        public async Task DotnetTrust_CertificateFingerPrintAction_TryAddSameFingerPrint_Fails(bool allowUntrustedRoot)
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var package             = new SimpleTestPackageContext();

            using (SimpleTestPathContext pathContext = _msbuildFixture.CreateSimpleTestPathContext())
                using (MemoryStream zipStream = await package.CreateAsStreamAsync())
                    using (TrustedTestCert <TestCertificate> trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        var certFingerprint   = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        var repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                        var signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(trustedTestCert.Source.Cert, package, pathContext.PackageSource, new Uri(repoServiceIndex));

                        var config = $@"<?xml version=""1.0"" encoding=""utf-8""?>
                <configuration>
                </configuration>";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, pathContext.WorkingDirectory, config);
                        var nugetConfigPath          = Path.Combine(pathContext.WorkingDirectory, nugetConfigFileName);
                        var allowUntrustedRootArg    = allowUntrustedRoot ? "--allow-untrusted-root" : string.Empty;
                        var allowUntruestedRootValue = allowUntrustedRoot ? "true" : "false";
                        var authorName = "MyCompanyCert";

                        // Act
                        CommandRunnerResult result = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust certificate {authorName} {certFingerprint} {allowUntrustedRootArg}  --algorithm SHA256 --configfile {nugetConfigPath}");

                        // Assert
                        result.Success.Should().BeTrue();
                        result.AllOutput.Should().Contain(string.Format(CultureInfo.CurrentCulture, _successfulAddTrustedSigner, "author", authorName));

                        // Try to add same certificate fingerprint should fail
                        result = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust certificate {authorName} {certFingerprint} {allowUntrustedRootArg}  --algorithm SHA256 --configfile {nugetConfigPath}", ignoreExitCode: true);

                        // Main assert
                        result.Success.Should().BeFalse();
                        result.AllOutput.Should().Contain("The certificate finger you're trying to add is already in the certificate fingerprint list");
                        result.AllOutput.Should().NotContain("--help");
                    }
        }
Exemple #18
0
        public async Task VerifyCommand_AuthorSignedPackage_WithUntrustedCertificate_AllowUntrustedRootIsSetTrue_WrongNugetConfig_Fails()
        {
            IX509StoreCertificate storeCertificate = _signFixture.UntrustedSelfIssuedCertificateInCertificateStore;

            // Arrange
            using (var pathContext = new SimpleTestPathContext())
            {
                var nupkg = new SimpleTestPackageContext("A", "1.0.0");

                //Act
                string signedPackagePath = await SignedArchiveTestUtility.AuthorSignPackageAsync(storeCertificate.Certificate, nupkg, pathContext.WorkingDirectory);

                string certificateFingerprintString = SignatureTestUtility.GetFingerprint(storeCertificate.Certificate, HashAlgorithmName.SHA256);

                // Arrange
                string nugetConfigPath  = Path.Combine(pathContext.WorkingDirectory, NuGet.Configuration.Settings.DefaultSettingsFileName);
                string nugetConfigPath2 = Path.Combine(pathContext.WorkingDirectory, "nuget2.config");
                // nuget2.config doesn't have change for trustedSigners
                File.Copy(nugetConfigPath, nugetConfigPath2);

                string trustedSignersSectionContent = $@"
    <trustedSigners>
        <author name=""MyCert"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""true"" />
        </author>
    </trustedSigners>
";
                SimpleTestSettingsContext.AddSectionIntoNuGetConfig(pathContext.WorkingDirectory, trustedSignersSectionContent, "configuration");

                //Act
                // pass custom nuget2.config file, but doesn't have trustedSigners section
                CommandRunnerResult verifyResult = _msbuildFixture.RunDotnet(
                    pathContext.WorkingDirectory,
                    $"nuget verify {signedPackagePath} --all --certificate-fingerprint {certificateFingerprintString} --certificate-fingerprint def --configfile {nugetConfigPath2}",
                    ignoreExitCode: true);

                // Assert
                // allowUntrustedRoot is not set true in nuget2.config, but in nuget.config, so verify fails.
                verifyResult.Success.Should().BeFalse();
                verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
                verifyResult.AllOutput.Should().Contain(_primarySignatureInvalidErrorCode);
            }
        }
Exemple #19
0
        public async Task Verify_RepositorySignedPackage_WithRepositoryItemUntrustedCertificate_AllowUntrustedRootSetTrue_Succeeds(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            IX509StoreCertificate storeCertificate = _signFixture.UntrustedSelfIssuedCertificateInCertificateStore;

            // Arrange
            using (var pathContext = new SimpleTestPathContext())
            {
                var    nupkg         = new SimpleTestPackageContext("A", "1.0.0");
                string testDirectory = pathContext.WorkingDirectory;
                await SimpleTestPackageUtility.CreatePackagesAsync(testDirectory, nupkg);

                string packagePath = Path.Combine(testDirectory, nupkg.PackageName);

                //Act
                string certificateFingerprintString = SignatureTestUtility.GetFingerprint(storeCertificate.Certificate, HashAlgorithmName.SHA256);
                string repoServiceIndex             = "https://serviceindex.test/v3/index.json";
                string signedPackagePath            = await SignedArchiveTestUtility.RepositorySignPackageAsync(storeCertificate.Certificate, packagePath, pathContext.PackageSource, new Uri(repoServiceIndex));

                // Arrange
                string trustedSignersSectionContent = $@"
    <trustedSigners>
        <repository name=""MyCert"" serviceIndex = ""{repoServiceIndex}"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
        </repository>
    </trustedSigners>
";
                SimpleTestSettingsContext.AddSectionIntoNuGetConfig(pathContext.WorkingDirectory, trustedSignersSectionContent, "configuration");
                string fingerprint = verifyCertificateFingerprint ? $"--certificate-fingerprint {certificateFingerprintString} --certificate-fingerprint def" : string.Empty;

                //Act
                CommandRunnerResult verifyResult = _msbuildFixture.RunDotnet(
                    testDirectory,
                    $"nuget verify {signedPackagePath} {fingerprint}",
                    ignoreExitCode: true);

                // Assert
                // If allowUntrustedRoot is set true in nuget.config then verify succeeds for cert with untrusted root.
                verifyResult.Success.Should().BeTrue();
                verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
            }
        }
Exemple #20
0
        public async Task VerifyCommand_AuthorSignedPackage_WithUntrustedCertificate_AllowUntrustedRootIsSetTrue_CorrectNugetConfig_Succeed()
        {
            // Arrange
            using (var pathContext = new SimpleTestPathContext())
                using (var testCertificate = new X509Certificate2(_testFixture.UntrustedSelfIssuedCertificateInCertificateStore))
                {
                    var nupkg = new SimpleTestPackageContext("A", "1.0.0");

                    //Act
                    string signedPackagePath = await SignedArchiveTestUtility.AuthorSignPackageAsync(testCertificate, nupkg, pathContext.WorkingDirectory);

                    string certificateFingerprintString = SignatureTestUtility.GetFingerprint(testCertificate, HashAlgorithmName.SHA256);

                    // Arrange
                    string nugetConfigPath  = Path.Combine(pathContext.WorkingDirectory, NuGet.Configuration.Settings.DefaultSettingsFileName);
                    string nugetConfigPath2 = Path.Combine(pathContext.WorkingDirectory, "nuget2.config");
                    File.Copy(nugetConfigPath, nugetConfigPath2);

                    string trustedSignersSectionContent = $@"
    <trustedSigners>
        <author name=""MyCert"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""true"" />
        </author>
    </trustedSigners>
";
                    SimpleTestSettingsContext.AddSectionIntoNuGetConfig(nugetConfigPath2, trustedSignersSectionContent, "configuration");

                    // Act
                    // pass custom nuget2.config file, it has trustedSigners section
                    CommandRunnerResult verifyResult = CommandRunner.Run(
                        _nugetExePath,
                        pathContext.PackageSource,
                        $"verify {signedPackagePath} -All -CertificateFingerprint {certificateFingerprintString};def -ConfigFile {nugetConfigPath2}",
                        waitForExit: true);

                    // Assert
                    // allowUntrustedRoot is set true in nuget2.config, so verify succeeds.
                    verifyResult.Success.Should().BeTrue();
                    verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
                }
        }
        public async Task DotnetTrust_AuthorAction_TryAddSameAuthor_Fails(bool allowUntrustedRoot)
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var package             = new SimpleTestPackageContext();

            using (SimpleTestPathContext pathContext = _msbuildFixture.CreateSimpleTestPathContext())
                using (MemoryStream zipStream = await package.CreateAsStreamAsync())
                    using (TrustedTestCert <TestCertificate> trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        string certFingerprint   = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        string signedPackagePath = await SignedArchiveTestUtility.AuthorSignPackageAsync(trustedTestCert.Source.Cert, package, pathContext.PackageSource);

                        var config = $@"<?xml version=""1.0"" encoding=""utf-8""?>
                <configuration>
                </configuration>";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, pathContext.WorkingDirectory, config);
                        var nugetConfigPath          = Path.Combine(pathContext.WorkingDirectory, nugetConfigFileName);
                        var allowUntrustedRootArg    = allowUntrustedRoot ? "--allow-untrusted-root" : string.Empty;
                        var allowUntruestedRootValue = allowUntrustedRoot ? "true" : "false";

                        // Act
                        CommandRunnerResult resultAdd = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust author nuget {signedPackagePath}  {allowUntrustedRootArg} --configfile {nugetConfigPath}");

                        // Assert
                        resultAdd.Success.Should().BeTrue();

                        // Try to add same author again.
                        resultAdd = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust author nuget {signedPackagePath}  {allowUntrustedRootArg} --configfile {nugetConfigPath}", ignoreExitCode: true);

                        // Main assert
                        resultAdd.Success.Should().BeFalse();
                        resultAdd.AllOutput.Should().Contain("error: A trusted signer 'nuget' already exists.");
                        resultAdd.AllOutput.Should().NotContain("--help");
                    }
        }
Exemple #22
0
        public async Task Verify_AuthorSignedPackage_WithRepositoryItemTrustedCertificate_Fails(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            // Arrange
            TrustedTestCert <TestCertificate> cert = _testFixture.TrustedTestCertificateChain.Leaf;

            using (var pathContext = new SimpleTestPathContext())
            {
                var    nupkg         = new SimpleTestPackageContext("A", "1.0.0");
                string testDirectory = pathContext.WorkingDirectory;
                await SimpleTestPackageUtility.CreatePackagesAsync(testDirectory, nupkg);

                //Act
                string certificateFingerprintString = SignatureTestUtility.GetFingerprint(cert.Source.Cert, HashAlgorithmName.SHA256);
                string signedPackagePath            = await SignedArchiveTestUtility.AuthorSignPackageAsync(cert.Source.Cert, nupkg, testDirectory);

                // Arrange
                string trustedSignersSectionContent = $@"
    <trustedSigners>
        <repository name=""MyCert"" serviceIndex=""{pathContext.PackageSource}"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
        </repository>
    </trustedSigners>
";
                SimpleTestSettingsContext.AddSectionIntoNuGetConfig(pathContext.WorkingDirectory, trustedSignersSectionContent, "configuration");
                string fingerprint = verifyCertificateFingerprint ? $"-CertificateFingerprint {certificateFingerprintString};def" : string.Empty;

                // Act
                CommandRunnerResult verifyResult = CommandRunner.Run(
                    _nugetExePath,
                    pathContext.PackageSource,
                    $"verify {signedPackagePath} -Signatures {fingerprint}",
                    waitForExit: true);

                // Assert
                verifyResult.Success.Should().BeFalse(because: verifyResult.AllOutput);
                verifyResult.AllOutput.Should().Contain(_noMatchingCertErrorCode);
                verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
                verifyResult.AllOutput.Should().Contain("This package is signed but not by a trusted signer.");
            }
        }
Exemple #23
0
        public async Task TrustedSignersCommand_AddTrustedSigner_WithAuthorSignedPackage_AddsMultipleFilesThrows(bool allowUntrustedRoot)
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var config = @"<?xml version=""1.0"" encoding=""utf-8""?>
<configuration>
</configuration>";

            // Arrange
            var nupkgA = new SimpleTestPackageContext("A", "1.0.0");
            var nupkgB = new SimpleTestPackageContext("B", "1.0.0");

            using (var dir = TestDirectory.Create())
                using (var zipStream = await nupkgA.CreateAsStreamAsync())
                    using (var trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        var certFingerprint    = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        var signedPackagePathA = await SignedArchiveTestUtility.AuthorSignPackageAsync(trustedTestCert.Source.Cert, nupkgA, dir);

                        var signedPackagePathB = await SignedArchiveTestUtility.AuthorSignPackageAsync(trustedTestCert.Source.Cert, nupkgB, dir);

                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, dir, config);
                        var nugetConfigPath       = Path.Combine(dir, nugetConfigFileName);
                        var allowUntrustedRootArg = allowUntrustedRoot ? "-AllowUntrustedRoot" : string.Empty;
                        var multiplePackagesPath  = $"{dir}{Path.DirectorySeparatorChar}*.nupkg";

                        // Act
                        var commandResult = CommandRunner.Run(
                            _nugetExePath,
                            dir,
                            $"trusted-signers add {multiplePackagesPath} -Name signer -Author {allowUntrustedRootArg} -Config {nugetConfigPath}",
                            waitForExit: true);

                        // Assert
                        commandResult.Success.Should().BeFalse();
                        commandResult.AllOutput.Should().Contain(string.Format(CultureInfo.CurrentCulture,
                                                                               "Multiple nupkg files detected on '{0}' path to trust, only 1 is allowed.",
                                                                               multiplePackagesPath));
                    }
        }
        public async Task VerifyCommand_VerifyOnPackageSignedWithAllowedCertificateSucceedsAsync()
        {
            // Arrange
            var cert    = _testFixture.TrustedTestCertificateChain.Leaf;
            var package = new SimpleTestPackageContext();

            using (var dir = TestDirectory.Create())
                using (var zipStream = await package.CreateAsStreamAsync())
                {
                    var packagePath = Path.Combine(dir, Guid.NewGuid().ToString());

                    zipStream.Seek(offset: 0, loc: SeekOrigin.Begin);

                    using (var fileStream = File.OpenWrite(packagePath))
                    {
                        zipStream.CopyTo(fileStream);
                    }

                    var signResult = CommandRunner.Run(
                        _nugetExePath,
                        dir,
                        $"sign {packagePath} -CertificateFingerprint {cert.Source.Cert.Thumbprint} -CertificateStoreName {cert.StoreName} -CertificateStoreLocation {cert.StoreLocation}",
                        waitForExit: true);

                    signResult.Success.Should().BeTrue();

                    var certificateFingerprintString = SignatureTestUtility.GetFingerprint(cert.Source.Cert, HashAlgorithmName.SHA256);

                    // Act
                    var verifyResult = CommandRunner.Run(
                        _nugetExePath,
                        dir,
                        $"verify {packagePath} -Signatures -CertificateFingerprint {certificateFingerprintString};abc;def",
                        waitForExit: true);

                    // Assert
                    verifyResult.Success.Should().BeTrue();
                    verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
                }
        }
Exemple #25
0
        public async Task Verify_AuthorSignedPackage_WithAuthorItemTrustedCertificate_Succeeds(string allowUntrustedRoot, bool verifyCertificateFingerprint)
        {
            // Arrange
            TrustedTestCert <TestCertificate> cert = _testFixture.TrustedTestCertificateChain.Leaf;

            using (var pathContext = new SimpleTestPathContext())
            {
                var    nupkg         = new SimpleTestPackageContext("A", "1.0.0");
                string testDirectory = pathContext.WorkingDirectory;
                await SimpleTestPackageUtility.CreatePackagesAsync(testDirectory, nupkg);

                //Act
                string certificateFingerprintString = SignatureTestUtility.GetFingerprint(cert.Source.Cert, HashAlgorithmName.SHA256);
                string signedPackagePath            = await SignedArchiveTestUtility.AuthorSignPackageAsync(cert.Source.Cert, nupkg, testDirectory);

                // Arrange
                string trustedSignersSectionContent = $@"
    <trustedSigners>
        <author name=""signed"">
            <certificate fingerprint=""{certificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""{allowUntrustedRoot}"" />
        </author>
    </trustedSigners>
";
                SimpleTestSettingsContext.AddSectionIntoNuGetConfig(testDirectory, trustedSignersSectionContent, "configuration");
                string fingerprint = verifyCertificateFingerprint ? $"-CertificateFingerprint {certificateFingerprintString};def" : string.Empty;

                // Act
                CommandRunnerResult verifyResult = CommandRunner.Run(
                    _nugetExePath,
                    testDirectory,
                    $"verify {signedPackagePath} -Signatures {fingerprint}",
                    waitForExit: true);

                // Assert
                // For certificate with trusted root setting allowUntrustedRoot to true/false doesn't matter
                verifyResult.Success.Should().BeTrue(because: verifyResult.AllOutput);
                verifyResult.AllOutput.Should().Contain(_noTimestamperWarningCode);
            }
        }
        public async Task DotnetTrust_RepositoryAction_TryAddSameRepository_Fails()
        {
            // Arrange
            var nugetConfigFileName = "NuGet.Config";
            var package             = new SimpleTestPackageContext();

            using (SimpleTestPathContext pathContext = _msbuildFixture.CreateSimpleTestPathContext())
                using (MemoryStream zipStream = await package.CreateAsStreamAsync())
                    using (TrustedTestCert <TestCertificate> trustedTestCert = SigningTestUtility.GenerateTrustedTestCertificate())
                    {
                        var certFingerprint   = SignatureTestUtility.GetFingerprint(trustedTestCert.Source.Cert, HashAlgorithmName.SHA256);
                        var repoServiceIndex  = "https://serviceindex.test/v3/index.json";
                        var signedPackagePath = await SignedArchiveTestUtility.RepositorySignPackageAsync(trustedTestCert.Source.Cert, package, pathContext.PackageSource, new Uri(repoServiceIndex));

                        var config = $@"<?xml version=""1.0"" encoding=""utf-8""?>
                <configuration>
                </configuration>";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigFileName, pathContext.WorkingDirectory, config);
                        var nugetConfigPath = Path.Combine(pathContext.WorkingDirectory, nugetConfigFileName);

                        // Act
                        CommandRunnerResult resultAdd = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust repository nuget {signedPackagePath} --configfile {nugetConfigPath}");

                        // Assert
                        resultAdd.Success.Should().BeTrue();

                        // Try to add same repository again
                        resultAdd = _msbuildFixture.RunDotnet(
                            pathContext.SolutionRoot,
                            $"nuget trust repository nuget {signedPackagePath} --configfile {nugetConfigPath}", ignoreExitCode: true);

                        // Main assert
                        resultAdd.Success.Should().BeFalse();
                        resultAdd.AllOutput.Should().Contain("error: A trusted signer 'nuget' already exists.");
                        resultAdd.AllOutput.Should().NotContain("--help");
                    }
        }
        public async Task GetTrustResultAsync_VerifyWithCertificateInRepoAllowList_Success_NoWarnAsync()
        {
            // Arrange
            var nupkg = new SimpleTestPackageContext();

            using (var dir = TestDirectory.Create())
                using (var testCertificate = new X509Certificate2(_trustedTestCert.Source.Cert))
                {
                    var certificateFingerprintString = SignatureTestUtility.GetFingerprint(testCertificate, HashAlgorithmName.SHA512);

                    var signedPackagePath = await SignedArchiveTestUtility.AuthorSignPackageAsync(testCertificate, nupkg, dir);

                    var allowListHashes = new[] { certificateFingerprintString, "abc" };
                    var allowList       = allowListHashes.Select(hash => new CertificateHashAllowListEntry(VerificationTarget.Primary, hash, HashAlgorithmName.SHA512)).ToList();

                    var trustProviders = new[]
                    {
                        new AllowListVerificationProvider()
                    };

                    var verifier         = new PackageSignatureVerifier(trustProviders);
                    var verifierSettings = GetSettings(allowUnsigned: false, allowUntrusted: false, clientAllowList: allowList, repoAllowList: null);

                    using (var packageReader = new PackageArchiveReader(signedPackagePath))
                    {
                        // Act
                        var result = await verifier.VerifySignaturesAsync(packageReader, verifierSettings, CancellationToken.None);

                        var resultsWithWarnings = result.Results.Where(r => r.GetWarningIssues().Any());
                        var totalWarningIssues  = resultsWithWarnings.SelectMany(r => r.GetWarningIssues());

                        // Assert
                        result.Valid.Should().BeTrue();
                        totalWarningIssues.Count().Should().Be(0);
                    }
                }
        }
        public async Task ClientPolicies_WithSignerInTrustedSignersListAsync(SigningTestType signature, SignaturePlacement trustedSigner, string validationMode)
        {
            // Arrange
            using (var dir = TestDirectory.Create())
                using (var authorCertificate = new X509Certificate2(_trustedAuthorTestCert.Source.Cert))
                    using (var repoCertificate = new X509Certificate2(_trustedRepoTestCert.Source.Cert))
                    {
                        var authorCertificateFingerprintString = SignatureTestUtility.GetFingerprint(authorCertificate, HashAlgorithmName.SHA256);
                        var repoCertificateFingerprintString   = SignatureTestUtility.GetFingerprint(repoCertificate, HashAlgorithmName.SHA256);

                        var signedPackagePath = await CreateSignedPackageAsync(dir, signature, authorCertificate, repoCertificate);

                        var trustedSignerString = "";

                        if (signature == SigningTestType.Author || (signature == SigningTestType.RepositoryCountersigned && trustedSigner == SignaturePlacement.PrimarySignature))
                        {
                            trustedSignerString = $@"<author name=""author1""><certificate fingerprint=""{authorCertificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""false"" /></author>";
                        }
                        else
                        {
                            trustedSignerString = $@"<repository name=""repo1"" serviceIndex=""https://api.v3serviceIndex.test/json""><certificate fingerprint=""{repoCertificateFingerprintString}"" hashAlgorithm=""SHA256"" allowUntrustedRoot=""false"" /></repository>";
                        }

                        var config = $@"
<configuration>
    <config>
        <add key=""signatureValidationMode"" value=""{validationMode}"" />
    </config>
    <trustedSigners>
        {trustedSignerString}
    </trustedSigners>
</configuration>";

                        var nugetConfigPath = "NuGet.Config";
                        SettingsTestUtils.CreateConfigurationFile(nugetConfigPath, dir, config);

                        // Act and Assert
                        var settings = new Settings(dir);

                        var clientPolicyContext = ClientPolicyContext.GetClientPolicy(settings, NullLogger.Instance);
                        var trustProviders      = new[]
                        {
                            new AllowListVerificationProvider(clientPolicyContext.AllowList, requireNonEmptyAllowList: clientPolicyContext.Policy == SignatureValidationMode.Require)
                        };
                        var verifier = new PackageSignatureVerifier(trustProviders);

                        using (var packageReader = new PackageArchiveReader(signedPackagePath))
                        {
                            // Act
                            var result = await verifier.VerifySignaturesAsync(packageReader, clientPolicyContext.VerifierSettings, CancellationToken.None);

                            var resultsWithWarnings = result.Results.Where(r => r.GetWarningIssues().Any());
                            var resultsWithErrors   = result.Results.Where(r => r.GetErrorIssues().Any());
                            var totalWarningIssues  = resultsWithWarnings.SelectMany(r => r.GetWarningIssues());
                            var totalErrorIssues    = resultsWithErrors.SelectMany(r => r.GetErrorIssues());

                            // Assert
                            result.IsValid.Should().BeTrue();
                            totalWarningIssues.Count().Should().Be(0);
                            totalErrorIssues.Count().Should().Be(0);
                        }
                    }
        }