使用 SQL FOR XML PATH,如何实现以下格式化的 XML 输出?
Using SQL FOR XML PATH, how can I achieve the following formatted XML output?
这个项目的范围比这个问题大得多。我接到了一个项目的任务,我不会让你厌烦私密的细节。最终我需要做的是将数据从数据库中取出并放入 XML 中,这样我就可以转换为 JSON 并创建一个简单的 Web 应用程序,它允许我解析和格式化数据满足客户需求的方式。
我确信有更好的方法来做到这一点,但这是我确定的路径..
我将大约 46,000 条记录转储到临时 Table。为了让您了解这些数据的结构 运行 以下查询:
SELECT
TransactionID,
OwnerID,
Date,
TransactionType,
ChargeCode,
Description,
DebitAmount
FROM #OwnerHistoryTemp
WHERE OwnerID = '11111111'
Returns这个:
TransactionID OwnerID Date TransactionType ChargeCode Description DebitAmount
28727 11111111 2014-12-01 E A1 APPLY CHARGES 210.00
28728 11111111 2014-12-03 C A1 DB11111111 210.00
28729 11111111 2015-01-01 E A1 APPLY CHARGES 183.37
我在这里要做的是使用 SQL FOR XML PATH(接受任何其他建议)输出数据,如下所示:
<OwnerHistory>
<OwnerID OwnerID="11111111">
<Transactions>
<TransactionID ID="28727">
<Date>2014-12-01</Date>
<TransactionType>E</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>210.00</DebitAmount>
</TransactionID>
<TransactionID ID="28728">
<Date>2014-12-03</Date>
<TransactionType>C</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>DB11111111</Description>
<DebitAmount>210.00</DebitAmount>
</TransactionID>
<TransactionID ID="28729">
<Date>2015-1-01</Date>
<TransactionType>E</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>183.37</DebitAmount>
</TransactionID>
</Transactions>
</OwnerID>
</OwnerHistory>
我的查询让我很接近,但还不够。因为同一个 OwnerID 出现多次(每个 TransactionID 出现一次),运行 下面的查询:
SELECT
OwnerID AS "@OwnerID",
TransactionID AS "Transaction/@RecordID",
Date AS "Transaction/Date",
TransactionType AS "Transaction/TransactionType",
ChargeCode AS "Transaction/ChargeCode",
Description AS "Transaction/Description",
DebitAmount AS "Transaction/DebitAmount"
FROM #OwnerHistoryTemp
WHERE OwnerID = '11111111'
GROUP BY OwnerID, RecordID, Date, ChargeCode, Description, DebitAmount
order by OwnerID
FOR XML PATH ('OwnerID'), ROOT('OwnerHistory')
Returns 如下:
<OwnerHistory>
<OwnerID OwnerID="11111111">
<Transaction RecordID="28727">
<Date>2014-12-01</Date>
<TransactionType>E</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>210.0000</DebitAmount>
</Transaction>
</OwnerID>
<OwnerID OwnerID="11111111">
<Transaction RecordID="28728">
<Date>2014-12-03</Date>
<TransactionType>C</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>DB11111111</Description>
<DebitAmount>210.0000</DebitAmount>
</Transaction>
</OwnerID>
<OwnerID OwnerID="11111111">
<Transaction RecordID="28729">
<Date>2015-01-01</Date>
<TransactionType>E</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>183.3700</DebitAmount>
</Transaction>
</OwnerID>
</OwnerHistory>
关于如何仅将 OwnerID 作为 Parent 提取一次并将所有事务分组在其下的任何想法?
可能是我不理解的简单问题,也可能是不可能的。如果是前者,请随意公开鞭打我...
准备好接受鞭打了吗?
嵌套您的查询以获得嵌套 XML,像这样:
SELECT TOP 1
OwnerID AS "@ID",
(SELECT
TransactionID AS "Transaction/@ID",
[Date] AS "Transaction/Date",
TransactionType AS "Transaction/Type",
ChargeCode AS "Transaction/ChargeCode",
[Description] AS "Transaction/Description",
DebitAmount AS "Transaction/DebitAmount"
FROM OwnerHistory
WHERE OwnerID = [Owner].OwnerID
FOR XML PATH(''), TYPE) Transactions
FROM OwnerHistory [Owner]
WHERE OwnerID = '11111111'
FOR XML PATH('Owner'), ROOT('OwnerHistory'), TYPE
结果XML:
<OwnerHistory>
<Owner ID="11111111">
<Transactions>
<Transaction ID="28727">
<Date>2015-03-26</Date>
<Type>E</Type>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>210.0000</DebitAmount>
</Transaction>
<Transaction ID="28728">
<Date>2015-03-26</Date>
<Type>C</Type>
<ChargeCode>A1</ChargeCode>
<Description>DB11111111</Description>
<DebitAmount>210.0000</DebitAmount>
</Transaction>
<Transaction ID="28729">
<Date>2015-03-26</Date>
<Type>E</Type>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>183.3700</DebitAmount>
</Transaction>
</Transactions>
</Owner>
</OwnerHistory>
请注意,包含 TOP 1
只是为了避免为包含 OwnerID
的每一行重复整个交易集。这可以通过多种方式处理;通常这种嵌套是连接两个规范化表的结果,因此只会出现 Owner
的一个实例。
MSDN 有一些很好的 examples 来演示此技术。
这个项目的范围比这个问题大得多。我接到了一个项目的任务,我不会让你厌烦私密的细节。最终我需要做的是将数据从数据库中取出并放入 XML 中,这样我就可以转换为 JSON 并创建一个简单的 Web 应用程序,它允许我解析和格式化数据满足客户需求的方式。
我确信有更好的方法来做到这一点,但这是我确定的路径..
我将大约 46,000 条记录转储到临时 Table。为了让您了解这些数据的结构 运行 以下查询:
SELECT
TransactionID,
OwnerID,
Date,
TransactionType,
ChargeCode,
Description,
DebitAmount
FROM #OwnerHistoryTemp
WHERE OwnerID = '11111111'
Returns这个:
TransactionID OwnerID Date TransactionType ChargeCode Description DebitAmount
28727 11111111 2014-12-01 E A1 APPLY CHARGES 210.00
28728 11111111 2014-12-03 C A1 DB11111111 210.00
28729 11111111 2015-01-01 E A1 APPLY CHARGES 183.37
我在这里要做的是使用 SQL FOR XML PATH(接受任何其他建议)输出数据,如下所示:
<OwnerHistory>
<OwnerID OwnerID="11111111">
<Transactions>
<TransactionID ID="28727">
<Date>2014-12-01</Date>
<TransactionType>E</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>210.00</DebitAmount>
</TransactionID>
<TransactionID ID="28728">
<Date>2014-12-03</Date>
<TransactionType>C</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>DB11111111</Description>
<DebitAmount>210.00</DebitAmount>
</TransactionID>
<TransactionID ID="28729">
<Date>2015-1-01</Date>
<TransactionType>E</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>183.37</DebitAmount>
</TransactionID>
</Transactions>
</OwnerID>
</OwnerHistory>
我的查询让我很接近,但还不够。因为同一个 OwnerID 出现多次(每个 TransactionID 出现一次),运行 下面的查询:
SELECT
OwnerID AS "@OwnerID",
TransactionID AS "Transaction/@RecordID",
Date AS "Transaction/Date",
TransactionType AS "Transaction/TransactionType",
ChargeCode AS "Transaction/ChargeCode",
Description AS "Transaction/Description",
DebitAmount AS "Transaction/DebitAmount"
FROM #OwnerHistoryTemp
WHERE OwnerID = '11111111'
GROUP BY OwnerID, RecordID, Date, ChargeCode, Description, DebitAmount
order by OwnerID
FOR XML PATH ('OwnerID'), ROOT('OwnerHistory')
Returns 如下:
<OwnerHistory>
<OwnerID OwnerID="11111111">
<Transaction RecordID="28727">
<Date>2014-12-01</Date>
<TransactionType>E</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>210.0000</DebitAmount>
</Transaction>
</OwnerID>
<OwnerID OwnerID="11111111">
<Transaction RecordID="28728">
<Date>2014-12-03</Date>
<TransactionType>C</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>DB11111111</Description>
<DebitAmount>210.0000</DebitAmount>
</Transaction>
</OwnerID>
<OwnerID OwnerID="11111111">
<Transaction RecordID="28729">
<Date>2015-01-01</Date>
<TransactionType>E</TransactionType>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>183.3700</DebitAmount>
</Transaction>
</OwnerID>
</OwnerHistory>
关于如何仅将 OwnerID 作为 Parent 提取一次并将所有事务分组在其下的任何想法?
可能是我不理解的简单问题,也可能是不可能的。如果是前者,请随意公开鞭打我...
准备好接受鞭打了吗?
嵌套您的查询以获得嵌套 XML,像这样:
SELECT TOP 1
OwnerID AS "@ID",
(SELECT
TransactionID AS "Transaction/@ID",
[Date] AS "Transaction/Date",
TransactionType AS "Transaction/Type",
ChargeCode AS "Transaction/ChargeCode",
[Description] AS "Transaction/Description",
DebitAmount AS "Transaction/DebitAmount"
FROM OwnerHistory
WHERE OwnerID = [Owner].OwnerID
FOR XML PATH(''), TYPE) Transactions
FROM OwnerHistory [Owner]
WHERE OwnerID = '11111111'
FOR XML PATH('Owner'), ROOT('OwnerHistory'), TYPE
结果XML:
<OwnerHistory>
<Owner ID="11111111">
<Transactions>
<Transaction ID="28727">
<Date>2015-03-26</Date>
<Type>E</Type>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>210.0000</DebitAmount>
</Transaction>
<Transaction ID="28728">
<Date>2015-03-26</Date>
<Type>C</Type>
<ChargeCode>A1</ChargeCode>
<Description>DB11111111</Description>
<DebitAmount>210.0000</DebitAmount>
</Transaction>
<Transaction ID="28729">
<Date>2015-03-26</Date>
<Type>E</Type>
<ChargeCode>A1</ChargeCode>
<Description>APPLY CHARGES</Description>
<DebitAmount>183.3700</DebitAmount>
</Transaction>
</Transactions>
</Owner>
</OwnerHistory>
请注意,包含 TOP 1
只是为了避免为包含 OwnerID
的每一行重复整个交易集。这可以通过多种方式处理;通常这种嵌套是连接两个规范化表的结果,因此只会出现 Owner
的一个实例。
MSDN 有一些很好的 examples 来演示此技术。