334 lines
15 KiB
PowerShell
334 lines
15 KiB
PowerShell
Import-Module (Join-Path -Path $PSScriptRoot 'certificateCommon.psm1') -Force
|
|
|
|
Describe "CmsMessage cmdlets and Get-PfxCertificate basic tests" -Tags "CI" {
|
|
|
|
BeforeAll {
|
|
$certLocation = New-GoodCertificate
|
|
$certLocation | Should Not BeNullOrEmpty | Out-Null
|
|
}
|
|
|
|
It "Verify Get-PfxCertificate -FilePath" {
|
|
$cert = Get-PfxCertificate -FilePath $certLocation
|
|
$cert.Subject | Should Be "CN=MyDataEnciphermentCert"
|
|
}
|
|
|
|
It "Verify Get-PfxCertificate -LiteralPath" {
|
|
$cert = Get-PfxCertificate -LiteralPath $certLocation
|
|
$cert.Subject | Should Be "CN=MyDataEnciphermentCert"
|
|
}
|
|
|
|
It "Verify Get-PfxCertificate positional argument" {
|
|
$cert = Get-PfxCertificate $certLocation
|
|
$cert.Subject | Should Be "CN=MyDataEnciphermentCert"
|
|
}
|
|
|
|
It "Verify CMS message recipient resolution by path" -Skip:(!$IsWindows) {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] $certLocation
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Encryption", [ref] $errors)
|
|
|
|
$recipient.Certificates.Count | Should Be 1
|
|
$recipient.Certificates[0].Subject | Should Match 'CN=MyDataEnciphermentCert'
|
|
}
|
|
|
|
It "Verify CMS message recipient resolution by cert" -Skip:(!$IsWindows) {
|
|
$errors = $null
|
|
$cert = Get-PfxCertificate $certLocation
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] $cert
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Encryption", [ref] $errors)
|
|
|
|
$recipient.Certificates.Count | Should Be 1
|
|
$recipient.Certificates[0].Subject | Should Match 'CN=MyDataEnciphermentCert'
|
|
}
|
|
|
|
It "Verify a CMS message can be protected / unprotected" -Skip:(!$IsWindows) {
|
|
$protected = "Hello World","How are you?" | Protect-CmsMessage -To $certLocation
|
|
$protected.IndexOf("-----BEGIN CMS-----") | Should Be 0
|
|
|
|
$message = $protected | Get-CmsMessage
|
|
$message.Recipients.Count | Should Be 1
|
|
$message.Recipients[0].IssuerName | Should Be "CN=MyDataEnciphermentCert"
|
|
|
|
$expected = "Hello World" + [System.Environment]::NewLine + "How are you?"
|
|
$decrypted = $message | Unprotect-CmsMessage -To $certLocation
|
|
$decrypted | Should Be $expected
|
|
|
|
$decrypted = $protected | Unprotect-CmsMessage -To $certLocation
|
|
$decrypted | Should Be $expected
|
|
}
|
|
}
|
|
|
|
|
|
Describe "CmsMessage cmdlets thorough tests" -Tags "Feature" {
|
|
|
|
BeforeAll{
|
|
if($IsWindows)
|
|
{
|
|
Install-TestCertificates
|
|
}
|
|
else
|
|
{
|
|
# Skip for non-Windows platforms
|
|
$defaultParamValues = $PSdefaultParameterValues.Clone()
|
|
$PSdefaultParameterValues = @{ "it:skip" = $true }
|
|
}
|
|
}
|
|
|
|
AfterAll {
|
|
if($IsWindows)
|
|
{
|
|
Remove-TestCertificates
|
|
}
|
|
else
|
|
{
|
|
$global:PSdefaultParameterValues = $defaultParamValues
|
|
}
|
|
}
|
|
|
|
It "Verify message recipient resolution by Base64Cert" {
|
|
$certContent = "
|
|
-----BEGIN CERTIFICATE-----
|
|
MIIDXTCCAkWgAwIBAgIQRTsRwsx0LZBHrx9z5Dag2zANBgkqhkiG9w0BAQUFADAh
|
|
MR8wHQYDVQQDDBZNeURhdGFFbmNpcGhlcm1lbnRDZXJ0MCAXDTE0MDcyNTIyMjkz
|
|
OVoYDzMwMTQwNzI1MjIzOTM5WjAhMR8wHQYDVQQDDBZNeURhdGFFbmNpcGhlcm1l
|
|
bnRDZXJ0MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAx3SuShUvnRqn
|
|
tYOIouJdP3wPZ5rtDi2KYPurpngGNZjM0EGDTrnhmEAI8DL4Kp6n/zz1mYVoX73+
|
|
6uCpZX/13VDXg1neebJ261XpBX6FzxtclIQr8ywdUtrEgCnUAhgqgvO1Wwm4ogNR
|
|
tWGCGkmlnqyaoV1j/V4KSn4WvKqSUIOZm0umGCTtNAJ6VtdpYO+uxxnRAapPUCY+
|
|
qQ7DFzTUECIo1lMlBcuMiXj6NSFr4/D7ltkZ27jCdsZmzI7ZvRnDlfSYTPQnAO/E
|
|
0uYn9uyKY/xfngWkUX/pe+j+10Lm1ypbASrj2Ezgf0KeZRXBwqKUOLhKheEmBJ18
|
|
rLV27qwHeQIDAQABo4GOMIGLMA4GA1UdDwEB/wQEAwIEMDAUBgNVHSUEDTALBgkr
|
|
BgEEAYI3UAEwRAYJKoZIhvcNAQkPBDcwNTAOBggqhkiG9w0DAgICAIAwDgYIKoZI
|
|
hvcNAwQCAgCAMAcGBSsOAwIHMAoGCCqGSIb3DQMHMB0GA1UdDgQWBBRIyIzwInLJ
|
|
3B+FajVUFMACf1hrxjANBgkqhkiG9w0BAQUFAAOCAQEAfFt4rmUmWfCbbwi2mCrZ
|
|
Osq0lfVNUiZ+iLlEKga4VAI3sJZRtErnVM70eXUt7XpRaOdIfxjuXFpsgc37KyLi
|
|
ByCORLuRC0itZVs3aba48opfMDXivxBy0ngqCPPLQsyaN9K7WnpvYV1QxiudYwwU
|
|
8U5rFmzlwNLvc3XiyoGWaVZluk2DIJawQ5QYAU9/NMBBCbPHjTG7k0l4cpcEC+Ex
|
|
od3RlO6/MOYuK2WB4VTxKsV80EdA3ljlu7Td8P4movnrbB4rG4wpCpk05eREkg/5
|
|
Y54Ilo9m5OSAWtdx4yfS779eebLgUs3P+dk6EKwovXMokVveZA8cenIp3QkqSpeT
|
|
cQ==
|
|
-----END CERTIFICATE-----
|
|
"
|
|
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] $certContent
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Encryption", [ref] $errors)
|
|
|
|
$recipient.Certificates.Count | Should Be 1
|
|
$recipient.Certificates[0].Subject | Should Match 'CN=MyDataEnciphermentCert'
|
|
}
|
|
|
|
It "Verify wildcarded recipient resolution by path [Decryption]" {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] ((Get-GoodCertificateLocation) + "*")
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Decryption", [ref] $errors)
|
|
|
|
# Should have resolved single cert
|
|
$recipient.Certificates.Count | Should Be 1
|
|
}
|
|
|
|
It "Verify wildcarded recipient resolution by path [Encryption]" {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] ((Get-GoodCertificateLocation) + "*")
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Encryption", [ref] $errors)
|
|
|
|
$recipient.Certificates.Count | Should Be 1
|
|
}
|
|
|
|
It "Verify resolution by directory" {
|
|
$protectedEventLoggingCertPath = Join-Path $TestDrive ProtectedEventLoggingDir
|
|
$null = New-Item -ItemType Directory $protectedEventLoggingCertPath -Force
|
|
Copy-Item (Get-GoodCertificateLocation) $protectedEventLoggingCertPath
|
|
Copy-Item (Get-GoodCertificateLocation) (Join-Path $protectedEventLoggingCertPath "SecondCert.pfx")
|
|
Copy-Item (Get-GoodCertificateLocation) (Join-Path $protectedEventLoggingCertPath "ThirdCert.pfx")
|
|
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] $protectedEventLoggingCertPath
|
|
$recipient.Resolve($executionContext.SessionState, "Decryption", [ref] $errors)
|
|
|
|
$recipient.Certificates.Count | Should Be 1
|
|
}
|
|
|
|
It "Verify resolution by thumbprint" {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] (Get-GoodCertificateObject).Thumbprint
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Decryption", [ref] $errors)
|
|
|
|
# "Should have certs from thumbprint in 'My' store"
|
|
$recipient.Certificates.Count | Should Be 1
|
|
$recipient.Certificates[0].Thumbprint | Should Be (Get-GoodCertificateObject).Thumbprint
|
|
}
|
|
|
|
It "Verify resolution by subject name" {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] (Get-GoodCertificateObject).Subject
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Decryption", [ref] $errors)
|
|
|
|
$recipient.Certificates.Count | Should Be 1
|
|
$recipient.Certificates[0].Thumbprint | Should Be (Get-GoodCertificateObject).Thumbprint
|
|
}
|
|
|
|
It "Verify error when no cert found in encryption for encryption" {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] "SomeCertificateThatDoesNotExist*"
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Encryption", [ref] $errors)
|
|
|
|
$errors.Count | Should Be 1
|
|
$errors[0].FullyQualifiedErrorId | Should Be "NoCertificateFound"
|
|
}
|
|
|
|
It "Verify error when encrypting to non-wildcarded identifier for decryption" {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] "SomeCertificateThatDoesNotExist"
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Decryption", [ref] $errors)
|
|
|
|
$errors.Count | Should Be 1
|
|
$errors[0].FullyQualifiedErrorId | Should Be "NoCertificateFound"
|
|
}
|
|
|
|
It "Verify error when encrypting to wrong cert" {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] (Get-BadCertificateObject).Thumbprint
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Encryption", [ref] $errors)
|
|
|
|
$errors.Count | Should Be 1
|
|
$errors[0].FullyQualifiedErrorId | Should Be "CertificateCannotBeUsedForEncryption"
|
|
}
|
|
|
|
It "Verify no error when encrypting to wildcarded identifier for decryption" {
|
|
$errors = $null
|
|
$recipient = [System.Management.Automation.CmsMessageRecipient] "SomeCertificateThatDoesNotExist*"
|
|
$recipient.Resolve($ExecutionContext.SessionState, "Decryption", [ref] $errors)
|
|
|
|
$errors | Should Be $null
|
|
$recipient.Certificates.Count | Should Be 0
|
|
}
|
|
|
|
It "Verify Protect-CmsMessage emits recipient errors" {
|
|
try {
|
|
"Hello World" | Protect-CmsMessage -To "SomeThumbprintThatDoesNotExist" -ErrorAction Stop
|
|
throw "No Exception!"
|
|
} catch {
|
|
$_.FullyQualifiedErrorId | Should Be "NoCertificateFound,Microsoft.PowerShell.Commands.ProtectCmsMessageCommand"
|
|
}
|
|
}
|
|
|
|
It "Verify CmsMessage cmdlets works with paths" {
|
|
try {
|
|
$randomNum = Get-Random -Minimum 1000 -Maximum 9999
|
|
$tempPath = Join-Path $TestDrive "$randomNum-Path-Test-File"
|
|
$encryptedPath = $tempPath + ".encrypted.txt"
|
|
"Hello World","How are you?" | Set-Content $tempPath
|
|
|
|
Protect-CmsMessage -Path $tempPath -To (Get-GoodCertificateLocation) -OutFile $encryptedPath
|
|
|
|
$message = Get-CmsMessage -LiteralPath $encryptedPath
|
|
$message.Recipients.Count | Should Be 1
|
|
$message.Recipients[0].IssuerName | Should Be "CN=MyDataEnciphermentCert"
|
|
|
|
$expected = "Hello World" + [System.Environment]::NewLine + "How are you?" + [System.Environment]::NewLine
|
|
$decrypted = $message | Unprotect-CmsMessage -To (Get-GoodCertificateLocation)
|
|
$decrypted | Should Be $expected
|
|
|
|
$decrypted = Unprotect-CmsMessage -Path $encryptedPath -To (Get-GoodCertificateLocation)
|
|
$decrypted | Should Be $expected
|
|
} finally {
|
|
Remove-Item $tempPath, $encryptedPath -Force -ErrorAction SilentlyContinue
|
|
}
|
|
}
|
|
|
|
It "Verify Unprotect-CmsMessage works with local store" {
|
|
try {
|
|
$randomNum = Get-Random -Minimum 1000 -Maximum 9999
|
|
$tempPath = Join-Path $TestDrive "$randomNum-Path-Test-File"
|
|
"Hello World" | Protect-CmsMessage -To (Get-GoodCertificateLocation) -OutFile $tempPath
|
|
|
|
# Decrypt using $importedCert in the Cert store
|
|
$decrypted = Unprotect-CmsMessage -Path $tempPath
|
|
$decrypted | Should Be "Hello World"
|
|
} finally {
|
|
Remove-Item $tempPath -Force -ErrorAction SilentlyContinue
|
|
}
|
|
}
|
|
|
|
It "Verify Unprotect-CmsMessage emits recipient errors" {
|
|
try {
|
|
"" | Unprotect-CmsMessage -To "SomeThumbprintThatDoesNotExist" -IncludeContext -ErrorAction Stop
|
|
throw "No Exception!"
|
|
} catch {
|
|
$_.FullyQualifiedErrorId | Should Be "NoCertificateFound,Microsoft.PowerShell.Commands.UnprotectCmsMessageCommand"
|
|
}
|
|
}
|
|
|
|
It "Verify failure to extract Ascii armor generates an error [Unprotect-CmsMessage]" {
|
|
try {
|
|
"Hello World" | Unprotect-CmsMessage -ErrorAction Stop
|
|
throw "No Exception!"
|
|
} catch {
|
|
$_.FullyQualifiedErrorId | Should Be "InputContainedNoEncryptedContentIncludeContext,Microsoft.PowerShell.Commands.UnprotectCmsMessageCommand"
|
|
}
|
|
}
|
|
|
|
It "Verify failure to extract Ascii armor generates an error [Get-CmsMessage]" {
|
|
try {
|
|
"Hello World" | Get-CmsMessage -ErrorAction Stop
|
|
throw "No Exception!"
|
|
} catch {
|
|
$_.FullyQualifiedErrorId | Should Be "InputContainedNoEncryptedContent,Microsoft.PowerShell.Commands.GetCmsMessageCommand"
|
|
}
|
|
}
|
|
|
|
It "Verify 'Unprotect-CmsMessage -IncludeContext' with no encrypted input" {
|
|
# Should have round-tripped content
|
|
$result = "Hello World" | Unprotect-CmsMessage -IncludeContext
|
|
$result | Should Be "Hello World"
|
|
}
|
|
|
|
It "Verify Unprotect-CmsMessage lets you include context" {
|
|
$protected = "Hello World" | Protect-CmsMessage -To (Get-GoodCertificateLocation)
|
|
$adjustedProtected = "Pre content" + [System.Environment]::NewLine + $protected + [System.Environment]::NewLine + "Post content"
|
|
|
|
$decryptedNoContext = $adjustedProtected | Unprotect-CmsMessage -To (Get-GoodCertificateLocation)
|
|
$decryptedWithContext = $adjustedProtected | Unprotect-CmsMessage -To (Get-GoodCertificateLocation) -IncludeContext
|
|
|
|
$decryptedNoContext | Should Be "Hello World"
|
|
|
|
$expected = "Pre content" + [System.Environment]::NewLine + "Hello World" + [System.Environment]::NewLine + "Post content"
|
|
$decryptedWithContext | Should Be $expected
|
|
}
|
|
|
|
It "Verify Unprotect-CmsMessage treats event logs as a first class citizen" {
|
|
$protected = "Encrypted Message1","Encrypted Message2" | Protect-CmsMessage -To (Get-GoodCertificateLocation)
|
|
$virtualEventLog = Get-WinEvent Microsoft-Windows-PowerShell/Operational -MaxEvents 1
|
|
$savedId = $virtualEventLog.Id
|
|
$virtualEventLog.Message = $protected
|
|
|
|
$expected = "Encrypted Message1" + [System.Environment]::NewLine + "Encrypted Message2"
|
|
$decrypted = $virtualEventLog | Unprotect-CmsMessage -To (Get-GoodCertificateLocation)
|
|
$decrypted | Should Be $expected
|
|
|
|
$processed = $virtualEventLog | Unprotect-CmsMessage -To (Get-GoodCertificateLocation) -IncludeContext
|
|
$processed.Id | Should Be $savedId
|
|
$processed.Message | Should Be $expected
|
|
}
|
|
|
|
# Pending due to #3847
|
|
It "Verify -DocumentEncryptionCert parameter works" -Pending {
|
|
$foundCerts = Get-ChildItem Cert:\CurrentUser -Recurse -DocumentEncryptionCert
|
|
|
|
# Validate they all match the EKU
|
|
$correctMatching = $foundCerts | Where-Object {
|
|
($_.EnhancedKeyUsageList.Count -gt 0) -and
|
|
($_.EnhancedKeyUsageList[0].ObjectId -eq '1.3.6.1.4.1.311.80.1')
|
|
}
|
|
# "All Document Encryption Cert should have had correct EKU"
|
|
@($foundCerts).Count | Should Be @($correctMatching).Count
|
|
}
|
|
|
|
It "Verify protect message using OutString" {
|
|
$protected = Get-Process -Id $pid | Protect-CmsMessage -To (Get-GoodCertificateLocation)
|
|
$decrypted = $protected | Unprotect-CmsMessage -To (Get-GoodCertificateLocation)
|
|
# Should have had PID in output
|
|
$decrypted | Should Match $pid
|
|
}
|
|
}
|