. $PSScriptRoot\..\..\Load-PesterModules.ps1 $here = Split-Path -Parent $MyInvocation.MyCommand.Path $sut = (Split-Path -Leaf $MyInvocation.MyCommand.Path) -replace '\.tests\.', '.' $functionPath = Join-Path -Path $here -ChildPath $sut Write-Host "Overriding SUT: $functionPath" Import-Module $functionPath -Force $moduleForMock = "" <# There are three potential use-cases in this exercise We modify external state and the caller will respond differently depending on that external state If nothing was ever wrong, we should see case #1 In the case the third party is busted outside of our interaction, we should see case #2 In the event that this function did the job it was intended to do, and everybody is happy, we should see case #3 Run first call second call #1 pass #2 throw throw #3 throw pass #> Describe "Start-FileBeatsService" { Mock -ModuleName $moduleForMock -CommandName Get-LogLeadName -MockWith { return "UUT" } Mock -ModuleName $moduleForMock -CommandName Get-WindowsServiceApplicationPath -MockWith { return $env:TEMP } Mock -ModuleName $moduleForMock -CommandName Stop-AlkamiService -MockWith { return $null } Mock -ModuleName $moduleForMock -CommandName Remove-FileSystemItem -MockWith { return $null } Mock -ModuleName $moduleForMock -CommandName Start-AlkamiService -MockWith { return $null } Mock -ModuleName $moduleForMock -CommandName Write-Warning -MockWith { } Mock -ModuleName $moduleForMock -CommandName Write-Host -MockWith { } Mock -ModuleName $moduleForMock -CommandName Test-Path -MockWith { return $false } Mock -ModuleName $moduleForMock -CommandName Split-Path -MockWith { return "dummy path" } Mock -ModuleName $moduleForMock -CommandName Join-Path -MockWith { return "dummy path" } Mock -ModuleName $moduleForMock -CommandName New-Item -MockWith { return $null } Context "Happiest Path" { Mock -ModuleName $moduleForMock -CommandName Get-FileBeatsService -MockWith { return @( @{ Name = 'Filebeat (Haystack)' DisplayName = 'Filebeat (Haystack)' State = 'Running' StartMode = 'Auto' ExePath = '"C:\Tools\Beats\FileBeat\tools\\filebeat.exe"' } ) } Mock -ModuleName $moduleForMock -CommandName Start-AlkamiService -MockWith { return $null } It "Exits cleanly with no throws" { { Start-FileBeatsService } | Should -Not -Throw } } Context "Start-AlkamiService throws every time (worst path)" { Mock -ModuleName $moduleForMock -CommandName Get-FileBeatsService -MockWith { return @( @{ Name = 'Filebeat (Haystack)' DisplayName = 'Filebeat (Haystack)' State = 'Running' StartMode = 'Auto' ExePath = '"C:\Tools\Beats\FileBeat\tools\\filebeat.exe"' } ) } # assume the external program just hates us and fails every time no matter what we do Mock -ModuleName $moduleForMock -CommandName Start-AlkamiService -MockWith { throw 'expected exception' } It "Tries to start service twice then throws an exception" { { Start-FileBeatsService } | Should -Throw Assert-MockCalled -CommandName Start-AlkamiService -ModuleName $moduleForMock -Times 2 -Exactly -Scope It } } Context "Start-AlkamiService throws the first time but works the next time (expected path)" { Mock -ModuleName $moduleForMock -CommandName Get-FileBeatsService -MockWith { return @( @{ Name = 'Filebeat (Haystack)' DisplayName = 'Filebeat (Haystack)' State = 'Running' StartMode = 'Auto' ExePath = '"C:\Tools\Beats\FileBeat\tools\\filebeat.exe"' }, @{ Name = 'Filebeat_os (Haystack)' DisplayName = 'Filebeat_os (Haystack)' State = 'Running' StartMode = 'Auto' ExePath = '"C:\Tools\Beats\FileBeat_os\tools\\filebeat.exe"' }) } $script:firstPassCompleted = $false $script:secondPassCompleted = $false $script:thirdPassCompleted = $false Mock -ModuleName $moduleForMock -CommandName Start-AlkamiService -MockWith { # track external state as tho we were actively making changes to the full system instead of mocking things # the actual target application will have two response states so we need to recognize that if ($script:firstPassCompleted -eq $false) { $script:firstPassCompleted = $true Write-Host "PESTER: threw the first time" throw 'expected exception' } elseif ($script:firstPassCompleted -eq $true -and $script:secondPassCompleted -eq $false) { $script:secondPassCompleted = $true Write-Host "PESTER: did not throw the second time" return } elseif ($script:firstPassCompleted -eq $true -and $script:secondPassCompleted -eq $true -and $script:thirdPassCompleted -eq $false) { $script:thirdPassCompleted = $true Write-Host "PESTER: threw the third time" throw 'expected exception' } elseif ($script:firstPassCompleted -eq $true -and $script:secondPassCompleted -eq $true -and $script:thirdPassCompleted -eq $true) { Write-Host "PESTER: did not throw the forth time" return } else { Write-Host "PESTER: Found unexpected flag state, check brain" return } } It "Tries to start each service twice for a total of four tries and does not throw an error" { { Start-FileBeatsService } | Should -Not -Throw Assert-MockCalled -CommandName Start-AlkamiService -ModuleName $moduleForMock -Times 4 -Exactly } } }