Powershell作用域处理v2/v3的未记录的更改



背景:我一直在写一个powershell脚本,将文件从Windows Server'08上的Sharpoint 2010实例(带有powershell 2.x)迁移到Windows Server'012上的Sharepoint 2013实例(带有powershell 3.x)。

问题:我有以下代码在两个PSSession上运行($param是参数值的哈希表)

Invoke-Command -session $Session -argumentlist $params -scriptblock `
{
    Param ($in)
    $params = $in # store parameters in remote session
    # need to run with elevated privileges to access sharepoint farm
    # drops cli stdout support (no echo to screen...)
    [Microsoft.SharePoint.SPSecurity]::RunWithElevatedPrivileges(
    {
        # start getting the site and web objects
        $site = get-spsite($params["SiteURL"])
    })
}

我注意到,在PS 2.x远程会话中,分配给$site也分配给了Invoke-Command的作用域中的同一变量,即作用域被传递,或者它们共享同一作用域BUT在PS 3.x远程会话中分配给$site不会更改Invoke-Command中的值(真正的子作用域)。

我的解决方案:我编写了一个函数来计算它调用的每个服务器上的正确作用域,然后使用返回值作为Get-VariableSet-Variable-Scope选项的输入。这解决了我的问题,并允许分配和访问变量。

Function GetCorrectScope
{
    # scoping changed between version 2 and 3 of powershell
    # in version 3 we need to transfer variables between the
    # parent and local scope.
    if ($psversiontable.psversion.major -gt 2)
    {
        $ParentScope = 1 # up one level, powershell version >= 3
    }else
    {
        $ParentScope = 0 # current level, powershell version < 3
    }
    $ParentScope
}

问题:Microsoft在哪里(如果有的话)记录了这一点?(我在TechNet的about_scope中找不到它,它说它适用于2.x和3.x,是我在其他问题中看到的标准参考)。

还有,有更好/合适的方法吗?

它在《WMF3发行说明》的"更改WINDOWS POWERSHELL语言"一节中有介绍。

代理在自己的范围中运行时执行的脚本块

Add-Type @"
public class Invoker
{
    public static void Invoke(System.Action<int> func)
    {
        func(1);
    }
}
"@
$a = 0
[Invoker]::Invoke({$a = 1})
$a
Returns 1 in Windows PowerShell 2.0 
Returns 0 in Windows PowerShell 3.0

相关内容

  • 没有找到相关文章

最新更新