You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为何Context -ForEach的变量无法传递到It块?该如何修复?

解决Pester中Context -ForEach变量无法传入InModuleScope的问题

问题根源

InModuleScope会创建独立的模块作用域,默认无法访问外部(Context -ForEach循环)的$Service变量,导致调用MyFunction时-Service参数为空,触发ValidateSet校验失败。

解决方案

方法1:通过-ArgumentList传递外部变量到InModuleScope

利用InModuleScope的-ArgumentList参数,将外部的$Service变量传入模块作用域内部,再通过param接收:

BeforeAll {
    Import-Module Pester
    Import-Module MyModule
}

Describe 'MyFunction' {
    BeforeAll {
        Mock -ModuleName MyModule Invoke-RestMethod { return @{ access_token = 'mocked access token' } }
    }

    Context 'When the service is <service>' -ForEach @(
        @{Service = 'MicrosoftGraph'}
        @{Service = 'SharePointOnline'}
    ) {
        It 'Should return an access token' {
            # 传递外部的$Service到InModuleScope内部
            InModuleScope MyModule -ArgumentList $Service {
                param($Service)
                
                Mock New-GraphJwtAssertion {}
                $TenantId = '<tenantId>'
                $ClientId = '<clientId>'
                $Certificate = <certificate>
                $result = MyFunction -TenantId $TenantId -ClientId $ClientId -Certificate $Certificate -Service $Service

                $result | Should -Be 'mocked access token'
            }
        }
    }
}

方法2:提前在模块作用域Mock私有函数

直接在Context的BeforeEach中,通过-ModuleName指定模块来Mock私有函数,避免进入InModuleScope,直接使用外部的$Service变量:

BeforeAll {
    Import-Module Pester
    Import-Module MyModule
}

Describe 'MyFunction' {
    BeforeAll {
        Mock -ModuleName MyModule Invoke-RestMethod { return @{ access_token = 'mocked access token' } }
    }

    Context 'When the service is <service>' -ForEach @(
        @{Service = 'MicrosoftGraph'}
        @{Service = 'SharePointOnline'}
    ) {
        BeforeEach {
            # 直接在模块作用域Mock私有函数
            Mock -ModuleName MyModule New-GraphJwtAssertion {}
        }

        It 'Should return an access token' {
            $TenantId = '<tenantId>'
            $ClientId = '<clientId>'
            $Certificate = <certificate>
            $result = MyFunction -TenantId $TenantId -ClientId $ClientId -Certificate $Certificate -Service $Service

            $result | Should -Be 'mocked access token'
        }
    }
}

方法对比

  • 方法1适合需要在单个It块内动态调整Mock逻辑的场景,灵活性更高。
  • 方法2更简洁,减少了作用域切换的复杂度,推荐优先使用。

内容的提问来源于stack exchange,提问作者Martin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.24 17:37:35