Reputation: 141
I am running below query on SQL Server 2014 server but I can't understand why I am getting only one row in result.
DECLARE @idoc int, @doc varchar(1000);
SET @doc ='
<ROOT>
<Customer CustomerID="VINET" ContactName="Paul Henriot">
<Order CustomerID="VINET" EmployeeID="5" OrderDate="1996-07-04T00:00:00">
<OrderDetail OrderID="10248" ProductID="11" Quantity="12"/>
<OrderDetail OrderID="10248" ProductID="42" Quantity="10">
<ReturnDetail ReturnOrderID="1111" ReturnDate="1996-08-04T00:00:00"/>
</OrderDetail>
</Order>
</Customer>
<Customer CustomerID="LILAS" ContactName="Carlos Gonzlez">
<Order CustomerID="LILAS" EmployeeID="3" OrderDate="1996-08-16T00:00:00">
<OrderDetail OrderID="10283" ProductID="72" Quantity="3"/>
</Order>
</Customer>
</ROOT>';
--Create an internal representation of the XML document.
EXEC sp_xml_preparedocument @idoc OUTPUT, @doc;
-- SELECT stmt using OPENXML rowset provider
SELECT *
FROM OPENXML (@idoc, '/ROOT/Customer/Order/OrderDetail/ReturnDetail',2)
WITH ( OrderID int '../@OrderID',
order_CustomerID varchar(10) '../../@CustomerID',
EmployeeID varchar(10) '../../@EmployeeID',
ContactName varchar(100) '../../../@ContactName',
CustomerID varchar(10) '../../@CustomerID',
OrderDate datetime '../../@OrderDate',
ProdID int '../@ProductID',
Qty int '../@Quantity',
ReturnOrderID int '@ReturnOrderID',
ReturnDate datetime '@ReturnDate'
);
How do I get all 3 records returned like below
Upvotes: 0
Views: 43
Reputation: 754488
You should use the built-in, native XQuery support (instead of the legacy OPENXML
stuff...).
Use this code to get all the details down to the <OrderDetail>
node (define your @doc
variable as XML
):
DECLARE @doc XML;
SET @doc = '......';
SELECT
OrderID = XOD.value('@OrderID', 'int'),
CustomerID = XCus.value('@CustomerID', 'varchar(20)'),
ContactName = XCus.value('@ContactName', 'varchar(50)'),
EmployeeID = XOrder.value('@EmployeeID', 'int'),
OrderDate = XOrder.value('@OrderDate', 'datetime'),
ProductID = XOD.value('@ProductID', 'int'),
Quantity = XOD.value('@Quantity', 'int'),
ReturnOrderID = RetD.value('@ReturnOrderID', 'int'),
ReturnDate = RetD.value('@ReturnDate', 'datetime')
FROM
@doc.nodes('/ROOT/Customer') AS XT(XCus)
CROSS APPLY
XCus.nodes('Order') AS XT2(XOrder)
CROSS APPLY
XOrder.nodes('OrderDetail') AS XT3(XOD)
OUTER APPLY
XOD.nodes('ReturnDetail') AS XT4(RetD)
For each "level" that might contain multiple nodes (like <Customer>
under <ROOT>
etc.), you need to use CROSS APPLY
and the .nodes()
XQuery function to get all the child nodes - not just one (first or arbitrary).
Upvotes: 3