Question:
I’m writing tests for a fairly complex script and there’s one particular function in the script that will output different series of logging messages to the user. I would like to assert whether a particular logging message is being displayed.
The main issue is that I don’t know what parameter is implicitly handling the text that I’m passing the Write-Host
cmdlet.
Here is some code that captures the premise of what I am trying to do…
Function to test
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
function TestFunction($TestInput) { if ($TestInput -contains 1) { Write-Host "TestInput contains a 1" } if ($TestInput -contains 3 ) { Write-Host "TestInput contains a 3" } if ($TestInput -contains 4 ) { Write-Host "TestInput contains a 4" } } |
Pester test
1 2 3 4 5 6 7 8 9 10 |
Describe "TestFunction" { It "should call Write-Host with appropriate message if 1 or 3 is passed" { Mock Write-Host {} TestFunction -TestInput @(1, 2, 3) Assert-MockCalled Write-Host -Exactly 2 -Scope It Assert-MockCalled Write-Host -Exactly 1 -Scope It -ParameterFilter { "TestInput contains a 1" } Assert-MockCalled Write-Host -Exactly 1 -Scope It -ParameterFilter { "TestInput contains a 3" } } } |
Output
1 2 3 4 5 6 7 8 |
Describing TestFunction [-] should call Write-Host with appropriate message if 1 or 3 is passed 19ms at 235: Assert-MockCalled Write-Host -Exactly 1 -Scope It -ParameterFilter { "TestInput contains a 1" } Expected Write-Host to be called 1 times exactly but was called 2 times Tests completed in 106ms Tests Passed: 0, Failed: 1, Skipped: 0, Pending: 0, Inconclusive: 0 |
Answer:
After reviewing the Microsoft documentation for the Write-Host
cmdlet, I found that there is an -Object
parameter. This accepts an array of generic objects to write to the console. The -Object
parameter is the parameter which needs to be specified in the -ParameterFilter
of the Pester tests in order to assert that the appropriate text is being displayed.
My updated code is as follows…
Function to test
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
function TestFunction($TestInput) { if ($TestInput -contains 1) { Write-Host "TestInput contains a 1" } if ($TestInput -contains 3 ) { Write-Host "TestInput contains a 3" } if ($TestInput -contains 4 ) { Write-Host "TestInput contains a 4" } } |
Pester test
1 2 3 4 5 6 7 8 9 10 |
Describe "TestFunction" { It "should call Write-Host with appropriate message if 1 or 3 is passed" { Mock Write-Host {} TestFunction -TestInput @(1, 2, 3) Assert-MockCalled Write-Host -Exactly 2 -Scope It Assert-MockCalled Write-Host -Exactly 1 -Scope It -ParameterFilter { $Object -eq "TestInput contains a 1" } Assert-MockCalled Write-Host -Exactly 1 -Scope It -ParameterFilter { $Object -eq "TestInput contains a 3" } } } |
Output
1 2 3 4 5 |
Describing TestFunction [+] should call Write-Host with appropriate message if 1 or 3 is passed 20ms Tests completed in 99ms Tests Passed: 1, Failed: 0, Skipped: 0, Pending: 0, Inconclusive: 0 |