1

SQL 2000 から SQL 2008 へのシステムのアップグレードである、いくつかのコードを本番環境に展開している最中です。

データベースからいくつかのデータを取得し、bcp を介していくつかのファイルを作成し (successfull)、いくつかの移動コマンドを実行しようとするストアド プロシージャの 1 つで、不思議な問題が発生しています。確実に存在し、サービスは sysadmin として実行されています。

実行しようとしているコードは次のとおりです。

set @cmd_string = 'move '+ @OutPath_AllCards + '*.* '+ @ArchivePath_AllCards
delete from @tbl_xp_cmdshell_output
Insert @tbl_xp_cmdshell_output exec @error_temp = master.dbo.xp_cmdshell @cmd_string

これは私が返すエラーメッセージです

xp_cmdshell Error Executing "move H:\Transfer\CHAD\Outbound\AllCards\*.* H:\Transfer\CHAD\Outbound\AllCards\Archive\" 

返されたコマンドラインエラーは

"The filename, directory name, or volume label syntax is incorrect."

これは、同じようにセットアップされた UAT バージョンのデータベースで正常に機能します。

助言がありますか?

アップデート:

ソース ディレクトリにファイルがない場合、エラーを再現できます。おそらくソースディレクトリにファイルがあるはずだと思いますが、 bcp によって作成されるまでにラグがあり、移動を実行するときにまだ存在していないのだろうか?何か案は?

4

2 に答える 2

0

データベースサーバー(あなたの場合はSQL Server)から外部OSコマンドを呼び出す場合、ローカルコンピューターはそのデータベースサーバーであり、必ずしもローカルコンピューターではないことに注意してください。

特定の例でH:ドライブについて言及したように、これはネットワークにマップされたドライブ(おそらく、ユーザーのホームフォルダーがあるドライブ)であると想定しています。ただし、このマッピングは UAT データベース サーバーには存在するが、PROD データベース サーバーには存在しないという状況になる可能性があります。DEV または UAT サーバーが誰かのローカル マシンに配置されていることは珍しくありません。ソフトウェアが展開の次の段階に移行すると、奇妙なことが起こり始めます。

あなたの場合、DOS のようなものではなく、UNC パス (先頭に二重のバックスラッシュを付けたもの) を使用する方がはるかに安全です。これにより、どこでもドライブ マッピングを独立させることができます。

しかし、個人的にはデータベース エンジンに OS 呼び出しを埋め込むのは好きではありません。私はシェル スクリプト (UNIX) またはコマンド スクリプト (Windows) を使用して、(isql、osql、または sqlplus を介して) ストアド プロシージャを呼び出してから、他の実行可能ファイルを実行することを好みます。BCP では、ストアド プロシージャから実行する利点はありません。BCP は独自の接続を開くため、ローカルの一時テーブルを使用することはできません。

また、操作が成功したかどうかを気にしないソース コードをよく見かけます。BCP では、成功したかどうかを検証するのにかなりの労力がかかります (常に 0 - 成功を返し、isql、osql、sqlplus などでも同じ話です)。エラーファイルをチェックし、それが空であることを確認して、問題がなかったと判断する必要があります。これらはすべて、ストアド プロシージャには適していません。もちろん、チェックのために別の実行可能ファイルを起動することもできますが、私の意見では、これは正しい方法ではありません。データベース サーバーは、アプリケーションを完全に実行するためではなく、データベース操作を想定しています。

それでも xp_cmdshell を放棄したくない場合は、その周りの汎用ラッパーとして独自のストアド プロシージャを作成することをお勧めします。データベース プロバイダーを変更することにした場合でも、移行の手間が大幅に軽減されます。

于 2012-10-26T03:03:20.293 に答える
0

OK、ここでちょっとした愚かなプログラマー (私と他の人たち) 症候群。

このエラーが発生するのは、move c:\Source*.* c:\dest ステートメントを実行すると、ソースにファイルがなく、発生したエラーが返されるためです (「ファイル名、ディレクトリ名、またはボリューム ラベルの構文が正しくありません。 」)。

コードは、前の実行からのファイルが存在すると想定しているため、新しいファイルを bcping する前に邪魔にならないように移動します。以前考えていたように、bcp は最初に発生しません。

ジョブの最初の実行では、前回の実行のファイルが存在しなかったため、エラーが発生しました。

したがって、解決策は、移動として実行するのではなく、コピーを実行してからフォルダー内で削除することだと思います。

于 2012-10-18T18:43:57.640 に答える