sql >> Database >  >> RDS >> Sqlserver

Hoe verwijder ik overtollige naamruimte in geneste query bij gebruik van FOR XML PATH?

Na uren van wanhoop en honderden proeven en fouten, heb ik de onderstaande oplossing bedacht.

Ik had hetzelfde probleem, toen ik slechts één . wilde xmlns attribuut, op de root knooppunt alleen . Maar ik had ook een zeer moeilijke vraag met veel subquery's en FOR XML EXPLICIT methode alleen was gewoon te omslachtig. Dus ja, ik wilde het gemak van FOR XML PATH in de subquery's en ook om mijn eigen xmlns . in te stellen .

Ik heb zo vriendelijk de code geleend van 8kb's antwoord, omdat het zo leuk was. Ik heb het een beetje aangepast voor een beter begrip. Hier is de code:

DECLARE @Order TABLE (OrderID INT, OrderDate DATETIME)    
DECLARE @OrderDetail TABLE (OrderID INT, ItemID VARCHAR(1), Name VARCHAR(50), Qty INT)    
INSERT @Order VALUES (1, '2010-01-01'), (2, '2010-01-02')    
INSERT @OrderDetail VALUES (1, 'A', 'Drink',  5),
                           (1, 'B', 'Cup',    2),
                           (2, 'A', 'Drink',  2),
                           (2, 'C', 'Straw',  1),
                           (2, 'D', 'Napkin', 1)

-- Your ordinary FOR XML PATH query
DECLARE @xml XML = (SELECT OrderID AS "@OrderID",
                        (SELECT ItemID AS "@ItemID", 
                                Name AS "data()" 
                         FROM @OrderDetail 
                         WHERE OrderID = o.OrderID 
                         FOR XML PATH ('Item'), TYPE)
                    FROM @Order o 
                    FOR XML PATH ('Order'), ROOT('dummyTag'), TYPE)

-- Magic happens here!       
SELECT 1 AS Tag
      ,NULL AS Parent
      ,@xml AS [xml!1!!xmltext]
      ,'http://test.com/order' AS [xml!1!xmlns]
FOR XML EXPLICIT

Resultaat:

<xml xmlns="http://test.com/order">
  <Order OrderID="1">
    <Item ItemID="A">Drink</Item>
    <Item ItemID="B">Cup</Item>
  </Order>
  <Order OrderID="2">
    <Item ItemID="A">Drink</Item>
    <Item ItemID="C">Straw</Item>
    <Item ItemID="D">Napkin</Item>
  </Order>
</xml>

Als u @xml heeft geselecteerd alleen zou je zien dat het root node dummyTag . bevat . We hebben het niet nodig, dus we verwijderen het met behulp van de richtlijn xmltext in FOR XML EXPLICIT vraag:

,@xml AS [xml!1!!xmltext]

Hoewel de uitleg in MSDN ingewikkelder klinkt, maar in de praktijk vertelt het de parser om de inhoud te selecteren van XML hoofdknooppunt.

Ik weet niet zeker hoe snel de vraag is, maar momenteel ontspan ik en drink ik whisky als een heer terwijl ik vredig naar de code kijk...



  1. MySQL REGEXP en herhaalde woorden

  2. SQL updatet rijen zonder de kolomnaam te kennen

  3. Filter een MySQL-resultaat in Delphi

  4. Een vergelijking tussen de MySQL Clone Plugin en Xtrabackup