繁体   English   中英

尝试将高级 function 作为 Powershell 中的 function 参数传递

[英]Trying to pass an advanced function as a function argument in Powershell

我有一个带有计算机名称的 CSV 文件。 我导入它们并希望使用每个值来做某事。

$computerNames = import-csv -Path "C:\Users\fakePath\Desktop\Programming\Powershell\remoteAddPrinters\computers.csv" -header "Computers"

function Iterate-CSV {
    param (
        # Parameter help description
        [Parameter(Mandatory=$true)]
        [array]
        $csvFilePath,

        [scriptblock]$functionCall #?
    )
    foreach ($computer in ($csvFilePath).Computers) { # Computer is the argument used in other functions.

        Write-Host $functionCall.Invoke($computer)
    }
}

这需要一个 csv 文件作为参数然后循环遍历它。 试图让这个 function 作为参数传递

function Add-NetworkPrinter {
    [CmdletBinding()]
    param (
        # Parameter help description
        [Parameter(Mandatory=$true, Position=0)]
        [String]
        $computerName
    )
    
    begin {
        $addPrinterCue = "\\printServer\printCue"
    }
    
    process { # This is a non-terminating error and cannot be handled by try/catch
        Write-Output "$addPrinterCue && $computerName"
        # invoke-command -ComputerName $computerName -scriptBlock {
        #     # cmd.exe /c rundll32 printui.dll,PrintUIEntry /gd /n$addPrinterCue
        #     cmd.exe /c rundll32 printui.dll,PrintUIEntry /ga /n$addPrinterCue /q
        #     Restart-Service -Name Spooler -Force
        #                                     #Creates error to handle
        # } -Credential $domainCredentials  #-ErrorVariable errmsg 2>$null
    }
    
    end {
        Write-Output "Successfully added printer to $computerName"
    }
}

这样我就不必编写另一个 foreach 循环来使用 CSV 中的值同步执行其他任务,我可以只使函数接受一个参数,即迭代变量

您需要传递一个调用您的scriptblock的脚本块。

$func = [scriptblock]{ 
    param ($arg)
    Add-NetworkPrinter $arg 
}

Iterate-CSV -csvFilePath ... -functionCall $func

要引用已注册 function 的底层脚本块定义,请使用function:驱动器前缀将其作为变量传递:

Iterate-Csv ... -scriptBlock ${function:Add-NetworkPrinter}

正如@Andrey 指出的那样,我没有创建名为 Add-NetworkPrinter 的高级 Function,而是创建了一个脚本块,同时保持我的高级 function 迭代 CSV 文件的值。

$computerNames = import-csv -Path "C:\fakePath\computers.csv" -header "Computers"

function Iterate-CSV {
    param (
        # Parameter help description
        [Parameter(Mandatory=$true)]
        [array]
        $csvFilePath,
        [scriptblock]$functionCall
    )
    foreach ($computer in ($csvFilePath).Computers) { 
        Write-Host $functionCall.Invoke($computer)
    }
}

$addNetworkPrinter = [scriptblock]{ 
    param ($computer)
    $addPrinterCue = "\\printServer\printCue"
    Write-Output "$addPrinterCue && $computer"
    # invoke-command -ComputerName $computerName -scriptBlock {
    #     # cmd.exe /c rundll32 printui.dll,PrintUIEntry /gd /n$addPrinterCue
    #     cmd.exe /c rundll32 printui.dll,PrintUIEntry /ga /n$addPrinterCue /q
    #     Restart-Service -Name Spooler -Force
    #                                     #Creates error to handle
    # } -Credential $domainCredentials  #-ErrorVariable errmsg 2>$null
}

$restarComputers = [scriptblock]{
    param (
        [Parameter(Mandatory=$true, Position=0)]
        [string]
        $computer
    )
    Write-Output "Restarting computer $computer"
    # Restart-Computer -ComputerName $computer -Credential $domainCredentials -Force
}

然后,我通过提供 csv 的路径作为 param1 和对 param2 使用相同值的脚本块来调用 Iterate-CSV function。 感谢您提供 ScriptBlock 信息!

Iterate-CSV -csvFilePath $computerNames -functionCall $addNetworkPrinter
Iterate-CSV -csvFilePath $computerNames -functionCall $restarComputers

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM