【问题标题】:$con.Open() doesn't work in foreach, but works when directly used$con.Open() 在 foreach 中不起作用,但直接使用时起作用
【发布时间】:2016-05-21 16:19:59
【问题描述】:

我有一个代码 sn-p 用于连接到 SQL Server 实例并进行查询,这工作正常。

$instance="Instance"
$DB = "master"
$sqlConnection = ConnectionString $Instance $DB
$sqlConnection = New-Object System.Data.SqlClient.SQLConnection($sqlConnection) 
$sqlConnection.Open()

但是,同样的代码 sn-p,如果放入一个 foreach 循环中,它必须遍历一组服务器,它就不起作用。

foreach ($instance in $Instances) {
    $instance
    $DB = "master"
    $sqlConnection = ConnectionString $Instance $DB
    $sqlConnection = New-Object System.Data.SqlClient.SQLConnection($sqlConnection) 
    $sqlConnection.Open()
}

错误:

使用“0”参数调用“Open”的异常:“建立与 SQL Server 的连接时发生与网络相关或特定于实例的错误。未找到或无法访问服务器。验证实例名称正确且 SQL Server 配置为允许远程连接。(提供程序:命名管道提供程序,错误:40 - 无法打开与 SQL Server 的连接)"

【问题讨论】:

  • 不要对不同的事物使用相同的验证(这里:$sqlConnection 用于连接字符串和连接对象)。在打开连接之前检查连接字符串。另外,函数 (?)ConnectionString 究竟做了什么?
  • 在使用相同的变量名打开一个新连接之前至少关闭连接。
  • 请考虑使用 Begin Process End 重新使用此类连接。作为奖励,您希望关闭 End 块内的连接。

标签: sql-server powershell foreach


【解决方案1】:

Ansgar 是正确的。你不应该重复使用变量名。

实现这一点的更简单方法是使用the Invoke-Query module,它将您的大部分代码折叠成一行。

$sql = "Update myTable set myColumn = 1;"
$db= "master"
$instances = ("instance1","instance2")
foreach ($instance in $instances)
    ## This command uses windows auth. 
    ## You can pass in a Credential object to use SqlServer auth.
    $rowcount = $sql | Invoke-SqlServerQuery -Server $instance -Database $db -CUD
   Write-Host "Updated $rowcount rows on server $instance."
}

免责声明:我是该模块的作者。

【讨论】:

  • 我觉得,当我从 foreach 运行这些类型的命令时,会出现一些不同的问题。如果我直接运行,所有这些都会运行,但不是在 foreach 下调用它们时。请指导我完成。
  • Invoke 调用应该在 foreach 循环内正常工作。你看到了什么错误/行为?您可以发布更多导致您出现问题的示例代码吗? (旁注:我刚刚更正了 rowcount 变量名称的错字。这是一个问题吗?)
猜你喜欢
  • 1970-01-01
  • 2021-01-07
  • 2017-04-04
  • 2021-12-13
  • 2019-06-27
  • 2015-07-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多