web-dev-qa-db-ja.com

SQLCMDでSQLステートメントの戻り値にアクセスする

DOSバッチファイルで実行するときにSQLステートメントの値を取得しようとしています...

sqlcmd -E -S DEVSERVER -Q "SELECT  COUNT(1) as [CaseCount] FROM Cases"

私はこの stackoverflow の質問のようにエラーレベルを追いかけているのではなく、データベースから返された実際のカウントを追いかけているので、追加のロジックを実行できます。

15
SteveC

_-o_ sqlcmdフラグを使用するか、標準の_>_リダイレクタを使用して、実行結果をテキストファイルに簡単に保存できます。次に、列ヘッダー(フラグ_-h_)を削除し、SQL Serverから行数(_SET NOCOUNT ON_)を削除することで、このファイルをフォーマットできます。

次のスクリプトは、COUNT(1)の値と改行のみを含むファイル_result.txt_を生成します。

_SQLCMD -E -S devserver -Q "SET NOCOUNT ON; SELECT COUNT(1) FROM Cases" -h -1 
  > result.txt
_

そして、値を読み戻します...

_set /p value=< result.txt
echo %value%
_
16
Gerardo Lima

FORバッチコマンドを使用してsqlcmd.exeを呼び出すことにより、余分な/一時ファイルを回避できます。

for /F usebackq %%i in (`sqlcmd -E -S "devserver,4711" -h-1 -Q "SET NOCOUNT ON; SELECT COUNT(1) ..."`) do (
    set count=%%i
)

if not defined count (
    echo Failed to execute SQL statement 1>&2
) else (
    echo %count%
)

いくつかの注意:

  • インタラクティブなCMD.EXEセッション、つまりコマンドラインから呼び出された場合は、%iの代わりに%%iを使用します。
  • -h-1オプションはsqlcmd.exeに列ヘッダーを抑制するように指示するため、出力は実際には1行のテキストのみです。
  • サーバーで架空のポート4711を使用して、「server、port」仕様全体を二重引用符で囲む必要があることを示しました。そうしないと、CMDのコマンドライン解析ルールにより、sqlcmdはサーバーとポートを個別の引数として認識し、失敗します。
19
Christian.K

@GerardoLimaからの回答は、そこまでの90%でした。さらに、先頭の空白を削除するには、set /aを使用して入力値を評価する必要があります。

これは@ Christian.Kからの回答では必要ありません

SQLCMD -E -S devserver -Q "SET NOCOUNT ON; SELECT COUNT(1) FROM Cases" -h -1 > result.txt
set /p raw=< result.txt
echo '%raw%'
set /a value=%raw%
echo '%value%'

私の出力は

'          0'
'0'
4
JJS