【问题标题】:invoke-sqlcmd via function throwing positional parameter error通过函数抛出位置参数错误调用 sqlcmd
【发布时间】:2019-09-23 03:42:24
【问题描述】:

我正在尝试使用函数来运行查询,但它似乎不接受我的服务器实例并给出错误:“Run-SqlCommand:找不到接受参数'mydbservername'的位置参数。”

当我在函数之外执行相同的 invoke-sqlcmd 时,它工作正常。

功能:

    function Run-SqlCommand
{
    [CmdletBinding()]
    Param
    (
        [parameter(Position=0, Mandatory=$True, ParameterSetName="Query")]
        [string]$Query,
        [parameter(Position=1, Mandatory=$True, ParameterSetName="DatabaseServerName")]
        [string]$DatabaseServerName,
        [parameter(Position=2, Mandatory=$True, ParameterSetName="Database")]
        [string]$Database,
        [parameter(Position=3, Mandatory=$True, ParameterSetName="Username")]
        [string]$Username,
        [parameter(Position=4, Mandatory=$True, ParameterSetName="Password")]
        [string]$Password
    )

    try {
        $result = Invoke-SqlCmd -query $Query -serverinstance $DatabaseServerName -Database $Database -Username $Username -Password $Password -ErrorAction Stop
        }
    catch {
        Write-Warning $_.Exception.Message
        }

}

在另一个脚本中,我定义了查询、服务器、数据库和用户/密码,并调用传递这些变量的函数:

$SuperUserQuery =@"
select uid,username,first_name,last_name,ad_username,active
from users
where (superuser = 'Y' AND active = '1')
Order by username Asc
"@

      $DatabaseServerName = "mydbservername"
      $Database = "dbname"
      $Username = "dbuser"
      $Password = "dbpass"


Run-SqlCommand $SuperUserQuery $DatabaseServerName $Database $Username $Password

当我这样做时,我得到了上面提到的错误:

“Run-SqlCommand : 找不到接受参数 'mydbservername' 的位置参数。”

如果我直接在脚本中运行 invoke-sqlcmd,我会尝试调用该函数 - 它工作得很好。

$result = Invoke-SqlCmd -query $SuperUserQuery -serverinstance $DatabaseServerName -Database $Database -Username $Username -Password $Password -ErrorAction Stop

为什么直接调用时它会起作用,而通过我的函数调用时不起作用?

好吧,我真的不明白为什么仍然希望有人帮助我理解....但是我通过更改参数来解决它...

        [parameter(Mandatory=$True)]
        [string]$Query,
        [parameter(Mandatory=$True)]
        [string]$DatabaseServerName,
        [parameter(Mandatory=$True)]
        [string]$Database,
        [parameter(Mandatory=$True)]
        [string]$Username,
        [parameter(Mandatory=$True)]
        [string]$Password

当我改变它时它起作用了。我想也许我不明白“位置”或“参数集名称”。

【问题讨论】:

  • 你为什么要在这里重新发明轮子?只使用Invoke-SqlCmd 有什么问题?

标签: sql-server function powershell invoke-sqlcmd


【解决方案1】:

我认为您正在尝试做的是所谓的Splatting。 通过 splatting,您可以构建易于阅读/维护的代码,尤其是当它涉及需要大量参数的 cmdlet 时。

为此,您创建一个 Hashtable 对象并将您想要用于 Invoke-Sqlcmd cmdlet 的所有参数放入其中,如下所示:

$sqlQuery = @"
SELECT uid,
       username,
       first_name,
       last_name,
       ad_username,
       active
FROM   users
WHERE  ( superuser = 'Y'
         AND active = '1' )
ORDER  BY username ASC 
"@

$sqlParams = @{
    'Query'          = $sqlQuery
    'ServerInstance' = 'mydbservername'
    'Database'       = 'dbname'
    'Username'       = 'dbuser'
    'Password'       = 'dbpass'
    # you can even add common parameters in there like
    'ErrorAction'    = 'Stop'
}

然后你这样使用它:

try {
    $result = Invoke-Sqlcmd @sqlParams
}
catch {
    Write-Warning $_.Exception.Message
}

【讨论】:

  • 有点——但我想多次使用该函数来运行不同的查询(并在未来将其用于其他脚本/项目),所以我不确定 splatting 是否正是我想要的寻找。我以前从未编写过 powershell 函数,所以我想我被参数迷住了。现在我将继续使用我所拥有的,直到我能弄清楚如何正确使用 Position 和 ParameterSetName。
猜你喜欢
  • 2019-12-21
  • 1970-01-01
  • 1970-01-01
  • 2019-04-23
  • 2022-01-23
  • 1970-01-01
  • 2019-01-16
  • 2020-10-22
  • 2017-05-17
相关资源
最近更新 更多