Assistance with AdventureWorks2019 query error "XQuery [Sales.Store.Demographics.value()]: There is no element named 'StoreSurvey'"

128 views Asked by At

I'm playing about with the AdventureWorks2019 database in SQL server. I was trying to find the relationship between store trading duration and revenue. The majority of this information is in the Sales.Store table but the date the store opened is contained within an XML document so I looked into how to access this information and came up with this query.

CREATE VIEW store_duration_revenue AS
WITH sub AS
(
  SELECT s.Name AS StoreName, s.Demographics.value ('(/StoreSurvey/YearOpened) [1]', 'int') AS YearOpened, YEAR(s.ModifiedDate) - s.Demographics.value ('(/StoreSurvey/YearOpened) [1]', 'int') AS TradingDuration, soh.TotalDue
  FROM Sales.Store AS s
  JOIN Sales.Customer AS c ON s.BusinessEntityID = c.StoreID
  JOIN Sales.SalesOrderHeader AS soh ON c.CustomerID = soh.CustomerID
)
SELECT StoreName, YearOpened, TradingDuration, SUM(TotalDue) AS Revenue
FROM sub
GROUP BY StoreName, YearOpened, TradingDuration;

I had thought this would be the correct way to do it but it is giving the error in the title. For reference here is the XML

<StoreSurvey xmlns="http://schemas.microsoft.com/sqlserver/2004/07/adventure-works/StoreSurvey">
  <AnnualSales>800000</AnnualSales>
  <AnnualRevenue>80000</AnnualRevenue>
  <BankName>United Security</BankName>
  <BusinessType>BM</BusinessType>
  <YearOpened>1996</YearOpened>
  <Specialty>Mountain</Specialty>
  <SquareFeet>21000</SquareFeet>
  <Brands>2</Brands>
  <Internet>ISDN</Internet>
  <NumberEmployees>13</NumberEmployees>
</StoreSurvey>

And here is a snippet of the table table snippet

My question is why doesnt this work the way I thought it would? and could someone assist in making it work as I intended it?

1

There are 1 answers

0
Yitzhak Khabinsky On BEST ANSWER

Here is how to query, a.k.a. shred, XML data type column with the default namespace.

SQL #1

USE AdventureWorks2019;
GO

WITH XMLNAMESPACES (DEFAULT 'http://schemas.microsoft.com/sqlserver/2004/07/adventure-works/StoreSurvey')
SELECT BusinessEntityID
    , c.value('(YearOpened)[1]', 'INT') AS YearOpened
    , c.value('(BankName)[1]', 'VARCHAR(30)') AS BankName
FROM sales.Store
CROSS APPLY demographics.nodes('/StoreSurvey') AS t(c);

SQL #2

WITH XMLNAMESPACES (DEFAULT 'http://schemas.microsoft.com/sqlserver/2004/07/adventure-works/StoreSurvey')
SELECT BusinessEntityID
    , demographics.value('(/StoreSurvey/YearOpened)[1]', 'INT') AS YearOpened
    , demographics.value('(/StoreSurvey/BankName)[1]', 'VARCHAR(30)') AS BankName
FROM sales.Store;

Output

BusinessEntityID YearOpened BankName
292 1996 United Security
294 1991 International Bank
296 1999 Primary Bank & Reserve
298 1994 International Security
300 1987 Guardian Bank