[英]Pester: not all mocked functions are intercepted
我有許多模塊,包括ModuleMain和ModuleSql 。 模塊之間存在相互依賴關系,因此 ModuleMain 中的Main-Function使用 ModuleSql 中的 4 個函數:
function Main-Function {
[CmdletBinding(SupportsShouldProcess=$true)]
# The following 4 lines are all wrapped in $PSCmdlet.ShouldProcess() and
# try {} catch {} logic. I have left that out in this post, but I mention
# it in case it is relevant.
$a = New-SqlConnection
$b = Invoke-SqlStoredProc -connection $a
$c = Invoke-SqlQuery -connection $a
Close-SqlConnection -connection $a | Out-Null
return $c
}
我創建了一個Function-Main1.tests.ps1文件來測試 Function-Main1。 起初我使用InModuleScope
但后來切換到使用-ModuleName
參數指定每個模擬的模塊。
Import-Module "ModuleMain" -Force
Describe "Main-Function" {
Mock -ModuleName ModuleMain New-SqlConnection {
return $true }
Mock -ModuleName ModuleMain Invoke-SqlStoredProc {
return $true }
Mock -ModuleName ModuleMain Invoke-SqlQuery {
return $true }
Mock -ModuleName ModuleMain Close-SqlConnection {
return $true }
Context "When calling Main-Function with mocked SQL functions" {
It "Calls each SQL function once" {
Assert-MockCalled -Scope Context -ModuleName ModuleMain -CommandName New-SqlConnecion -Times 1 -Exactly
Assert-MockCalled -Scope Context -ModuleName ModuleMain -CommandName Invoke-SqlStoredProc -Times 1 -Exactly
Assert-MockCalled -Scope Context -ModuleName ModuleMain -CommandName Invoke-SqlQuery -Times 1 -Exactly
Assert-MockCalled -Scope Context -ModuleName ModuleMain -CommandName Close-SqlConnecion -Times 1 -Exactly
}
}
}
當我運行這個測試時,我得到以下結果:
[-] Calls each SQL function once 223ms
Expected Invoke-SqlStoredProc in module ModuleMain to be called 1 times exactly but was called 0 times
at line: xx in
xx: Assert-MockCalled -Scope Context -ModuleName ModuleMain -CommandName Invoke-SqlStoredProc -Times 1 -Exactly
請注意以下事項:
-ModuleName
設置為定義Main-Function的模塊,而不是定義 SQL 函數(我試圖模擬的)的模塊。InModuleScope
和-ModuleName
,例如將一個或另一個設置為ModuleSQL ,但主要是這讓事情變得更糟。 通過在其他模擬函數中添加 Verbose 輸出,我確認New-SqlConnection
和Close-SqlConnection
都被攔截,但Invoke-SqlStoredProc
和Invoke-SqlQuery
沒有被攔截。
深入探究,我可以看到Invoke-Sql*
( Invoke-Sql*
)函數拋出以下異常:錯誤:“從 'System.Boolean' 到 'System.Data.SqlClient.SqlConnection' 的無效轉換。” 這是我在調用這些函數的真實版本時所期望的行為,但我期望模擬版本會忽略參數類型。
為什么 Pester 只會攔截我的 4 個函數中的 2 個?
因此,在上面的評論中給出了對這個問題的簡短回答:
模擬函數不會忽略參數類型。 --寵物系列
這意味着當我嘗試調用Invoke-Sql*
函數並使用虛假的$sqlConnection變量(簡單地設置為$true )時,這會導致錯誤,因為輸入參數不是預期的數據類型。
在我的情況下,解決方案是模擬New-SqlConnection
函數,因此它返回一個[System.Data.SqlCient.SqlConnection]
對象。 碰巧的是,我也恢復使用InModuleScope
而不是在每個 Mock 上指定模塊:
InModuleScope "ModuleMain" {
Describe "MainFunction" {
Mock New-SqlConnection {
New-Object -TypeName System.Data.SqlCient.SqlConnection
}
...
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.