私は、Xqueryを使用してテーブルのコレクションの変更の追跡を処理するサービスブローカーを作成する任務を負っています。メッセージを渡す方法を理解しました(列名のxmlと、ステートメントの更新および削除されたテーブル)。目的は、列名のリストを取得し、変更ではなく、更新/削除された各行の同様の列を比較することです。
XMLのサンプルは次のとおりです。
<Update xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<TableName>
<ID>2414</ID>
<fkEvent>2664</fkEvent>
<fkType xsi:nil="true" />
<Description>Phil Test 3</Description>
<DTS>2011-04-04T14:01:36.533</DTS>
<uID>192204FA-612F-46F4-A6CB-1B4D53769A81</uID>
<VersionID xsi:nil="true" />
<UpdateDateTime>2011-04-04T14:04:31.013</UpdateDateTime>
<DeleteFlag>0</DeleteFlag>
<Updated>0</Updated>
<Owner>42</Owner>
<CreatedBy>42</CreatedBy>
</TableName>
</Update>
によって生成されます:
SET @xml1 = (SELECT * FROM TableName ORDER BY ID DESC FOR XML AUTO, ELEMENTS XSINIL, ROOT('MsgEnv'))
私は次のコードを持っています:
WHILE @cnt <= @totCnt BEGIN
SELECT @child = @ColNames.query('/Columns/name[position()=sql:variable("@cnt")]')
SET @CurrentCol = REPLACE(REPLACE(CAST(@child AS VARCHAR(500)), '<name>', ''), '</name>', '')
PRINT @CurrentCol
WHILE @updateCnt <= @updateCntTotal BEGIN
SELECT @childUpdate = @xml1.query('/Update/TableName/sql:variable("@CurrentCol")')
PRINT CAST(@childUpdate AS VARCHAR(MAX))
WHILE @deleteCnt <= @deleteCntTotal BEGIN
SELECT @deleteCnt = @deleteCnt + 1
END
SET @deleteCnt = 1
SELECT @updateCnt = @updateCnt + 1
END
SET @updateCnt = 1
SELECT @cnt = @cnt + 1
END
私が抱えている問題は、このステートメントの列名を動的に設定することです。
SELECT @childUpdate = @xml1.query('/Update/TableName/sql:variable("@CurrentCol")')
sql:variableを使用していくつかの異なるバリエーションを試しました。これを行うことはできませんか?変更を「監査」する必要のあるテーブルがたくさんあるので、これを動的に実行できるようにしたいと思います。
編集1:
SELECT @childUpdate = @xml1.query('/Update/TableName/*[name() = sql:variable("@CurrentCol")]')
このエラーが発生します(()内の。を含む)も同様の効果があります。
Msg 2395, Level 16, State 1, Line 34
XQuery [query()]: There is no function '{http://www.w3.org/2004/07/xpath-functions}:name()'