【问题标题】:How to use Invoke-Sqlcmd from inside SSMS?如何在 SSMS 中使用 Invoke-Sqlcmd?
【发布时间】:2021-01-21 18:18:36
【问题描述】:

我从不同的服务器运行下面的查询(从 powershell 内部),一切都很好:

Invoke-Sqlcmd -Query "
SELECT [ServerName]=@@servername,m.Match_id, m.HostfamilyId, hf.NIEFlag, ra.DS2019Sent 
FROM APIA_Repl_pub.dbo.repl_HostFamily hf 
INNER JOIN APIA_Repl_pub.dbo.repl_Match m ON m.HostfamilyId =  hf.HostFamilyID
INNER JOIN APIA_Repl_Pub.dbo.repl_Aupair ra on ra.AuPairID = m.AupairId
WHERE ra.JunoCore_applicationID = 459630
" -ServerInstance "CTSTGDB"

我什至有时会在几台服务器上运行相同的查询来比较它们,以下面的结果为例:

我只想从 SSMS 内部运行相同的查询,但看看我做了什么以及得到了什么:

(我什至简化了查询,但仍然出现以下错误)

 GO
 declare @sql varchar(8000)
  SET @SQL=N'powershell.exe -command Invoke-Sqlcmd -Query "SELECT [ServerName]=@@servername" -ServerInstance "CTSTGDB"'

IF OBJECT_ID('tempdb..#Radhe','U') IS NOT NULL
   DROP TABLE #RADHE

CREATE TABLE #RADHE(I INT NOT NULL IDENTITY(1,1) PRIMARY KEY CLUSTERED, OUTPUT NVARCHAR(4000))

INSERT INTO #RADHE
 EXEC xp_cmdshell @sql

 SELECT * FROM #RADHE

 GO

OUTPUT
Invoke-Sqlcmd : A positional parameter cannot be found that accepts argument 
'[ServerName]=@@servername'.
At line:1 char:1
+ Invoke-Sqlcmd -Query SELECT [ServerName]=@@servername -ServerInstance ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidArgument: (:) [Invoke-Sqlcmd], ParameterB 
   indingException
    + FullyQualifiedErrorId : PositionalParameterNotFound,Microsoft.SqlServer. 
   Management.PowerShell.GetScriptCommand

 
NULL

我发现了一篇有趣的文章:

6 methods to write PowerShell output to a SQL Server table

它与我的工作方式相关或可以替代我的工作方式。

从 SSMS 内部 Invoke-Sqlcmd 到底是什么问题?

【问题讨论】:

  • Invoke-Sqlcmd 是一个 Powershell 命令,你不要在 SSMS 中使用它;这是 SQL Server 的 IDE。您可以为 powershell 使用 IDE,或者只使用 CLI。
  • SSMS 是您执行 SQL 查询的地方。你为什么要在 SSMS 中执行 powershell 脚本?那是零意义。只需使用查询本身。您已经处于 SQL 查询执行环境中。删除整个 'powershell.exe -command Invoke-Sqlcmd -Query "' 前缀和结束引号,并删除 EXEC xp_cmdshell \@sql。也不要将其分配给 \@sql。只需执行查询。直接。这就是 SSMS 的用途。
  • 也许是一个更直接的问题:当 SQLCMD 只是 SSMS GUI 的命令行版本时,为什么要尝试从 SSMS 中调用 SQLCMD?这是多余的。

标签: sql-server powershell ssms sql-server-2016 invoke-sqlcmd


【解决方案1】:

据我了解,您很难针对与查询所连接的服务器不同的服务器执行查询。好吧,我可以想到至少 2 种在 SSMS 中执行此操作的方法:

  1. 如果您当前的服务器有一个链接服务器,您可以使用EXEC statementAT 子句,如下所示:
declare @Sql nvarchar(max) = N'SELECT [ServerName]=@@servername,m.Match_id,
  m.HostfamilyId, hf.NIEFlag, ra.DS2019Sent 
FROM APIA_Repl_pub.dbo.repl_HostFamily hf 
  INNER JOIN APIA_Repl_pub.dbo.repl_Match m ON m.HostfamilyId =  hf.HostFamilyID
  INNER JOIN APIA_Repl_Pub.dbo.repl_Aupair ra on ra.AuPairID = m.AupairId
WHERE ra.JunoCore_applicationID = 459630';

-- This example assumes that the linked server name is the same as the remote server itself
exec (@Sql) at [CTSTGDB];
  1. 如果链接服务器不可用,您可以使用SQLCMD mode 进行查询:
:connect CTSTGDB
go

SELECT [ServerName]=@@servername,m.Match_id, m.HostfamilyId, hf.NIEFlag, ra.DS2019Sent 
FROM APIA_Repl_pub.dbo.repl_HostFamily hf 
INNER JOIN APIA_Repl_pub.dbo.repl_Match m ON m.HostfamilyId =  hf.HostFamilyID
INNER JOIN APIA_Repl_Pub.dbo.repl_Aupair ra on ra.AuPairID = m.AupairId
WHERE ra.JunoCore_applicationID = 459630;
go

:exit
go

此模式可以通过查询 -> SQLCMD 模式菜单选项来切换。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-11
    • 1970-01-01
    • 2013-06-09
    • 2016-11-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多