Solved

Using a WHERE in a Select Statement in SQL 2005 and Extract Parts of a Node Field

Posted on 2010-09-03
3
228 Views
Last Modified: 2012-05-10
I have a couple of questions regarding XML and doing a select query in SQL Server 2005.  I need to extract some parts of a field and I need to end my query with a  WHERE clause.

I first insert the XML file into a table like this:

INSERT INTO OrdersXML(xmlCol)
SELECT CONVERT (xml, A.Col1, 2)
FROM OPENROWSET( BULK '\\myfolder\Orders.xml', SINGLE_BLOB) AS A(Col1)

This is a sample of the CustomerInfo field containing the customer info.  I need to extract the First Name, Last name, and Customer Number from this field.  


<CustomerInfo>First Name = John
Last Name = Smith
CustomerNumber = 123456
shippingID = 654321
</CustomerInfo>

In this field, the labels are always going to be the same

First Name =
Last Name =
CustomerNumber =
shippingID =
 
Only the actual name, cust. number and ID changes. Also, notice there's a line break for each part.

And this is my select statement.

SELECT  
c.value('(Shipping/Products/Product/CustomerInfo)[1]', 'varchar(200)'),--I need the First selected.
c.value('(Shipping/Products/Product/CustomerInfo)[1]', 'varchar(200)'),-- I need the Last Name selected.
c.value('(Shipping/Products/Product/CustomerInfot)[1]', 'varchar(200)'),-- I need the Customer Number selected.
c.value('(Shipping/Products/Product/SKU)[1]', 'varchar(10)'), -- This is will part of the WHERE statement.
c.value('(Billing/NameParts/FirstName)[1]', 'varchar(50)'),
c.value('(Billing/NameParts/LastName)[1]', 'varchar(50)'),  
c.value('(Billing/Address/Street1)[1]', 'varchar(50)'),
c.value('(Billing/Address/Street2)[1]', 'varchar(50)'),
c.value('(Billing/Address/City)[1]', 'varchar(50)'),
c.value('(Billing/Address/State)[1]', 'varchar(2)'),
c.value('(Billing/Address/Code)[1]', 'varchar(6)'),  
c.value('(Billing/Address/Country)[1]', 'varchar(10)'),
c.value('(Payment/CreditCard/Issuer)[1]', 'varchar(50)'),
c.value('(OrderDate)[1]', 'datetime'),
c.value('(ShopSiteTransactionID)[1]', 'varchar(300)'),
c.value('(OrderNumber)[1]', 'int'),
c.value('(Other/Comments)[1]', 'varchar(300)')
FROM OrdersXML CROSS APPLY XMLCol.nodes('AllOrders/Order') T(c)

Right now, if I run this select query I can get all the records.  However, I need to be able to select only the records containing a certain SKU, so I will need a WHERE clause that looks for a particular SKU value. I don't know how to make this work.

Therefore, my selected records would like this:

John, Smith, 123456, BMW302, Donald, Trump, 1234 Hollywood Blvd, Los Angeles, ETC.

Does anyone knows how to accomplish this?

Thanks!




0
Comment
Question by:TheUndecider
  • 2
3 Comments
 
LVL 24

Accepted Solution

by:
DBAduck - Ben Miller earned 500 total points
ID: 33598589
Have you tried to use the WHERE with the statement you flagged?
SELECT  
c.value('(Shipping/Products/Product/CustomerInfo)[1]', 'varchar(200)'),--I need the First selected.
c.value('(Shipping/Products/Product/CustomerInfo)[1]', 'varchar(200)'),-- I need the Last Name selected.
c.value('(Shipping/Products/Product/CustomerInfot)[1]', 'varchar(200)'),-- I need the Customer Number selected.
c.value('(Shipping/Products/Product/SKU)[1]', 'varchar(10)'), -- This is will part of the WHERE statement.
c.value('(Billing/NameParts/FirstName)[1]', 'varchar(50)'),
c.value('(Billing/NameParts/LastName)[1]', 'varchar(50)'),  
c.value('(Billing/Address/Street1)[1]', 'varchar(50)'),
c.value('(Billing/Address/Street2)[1]', 'varchar(50)'),
c.value('(Billing/Address/City)[1]', 'varchar(50)'),
c.value('(Billing/Address/State)[1]', 'varchar(2)'),
c.value('(Billing/Address/Code)[1]', 'varchar(6)'),  
c.value('(Billing/Address/Country)[1]', 'varchar(10)'),
c.value('(Payment/CreditCard/Issuer)[1]', 'varchar(50)'),
c.value('(OrderDate)[1]', 'datetime'), 
c.value('(ShopSiteTransactionID)[1]', 'varchar(300)'),
c.value('(OrderNumber)[1]', 'int'),
c.value('(Other/Comments)[1]', 'varchar(300)')
FROM OrdersXML CROSS APPLY XMLCol.nodes('AllOrders/Order') T(c)
WHERE c.value('(Shipping/Products/Product/SKU)[1]', 'varchar(10)') = 'SKUVALUE'

Open in new window

0
 

Author Comment

by:TheUndecider
ID: 33599713
Hello dbaduck,

Thanks for replying.  I believe you're in the right path.  I tried what you suggested at first it did not work because I was looking for a particular SKU in a order containing 3 products.  It was the second one.

Therefore, if I modify the where clause to:

WHERE c.value('(Shipping/Products/Product/SKU)[2]', 'varchar(10)') = 'SKUVALUE'

I guess I was not couting on the fact that someone can order more than one product in the same orderl.  

How can I select the records based on All the products instead of the orders?  I assuming the [1]  in the Shipping/Products/Product/SKU)[1] will have to change to some kind  of variable.
0
 

Author Comment

by:TheUndecider
ID: 33600442
Hi again,

I kept on going on based on your suggestion and I was able to do the proper WHERE clause.  

I figured out products are the fields I needed to base my query on because those are the ones that can be more than one.

therefore, I changed the FROM statement to

    FROM OrdersXML CROSS APPLY XMLCol.nodes('AllOrders/Order/Shipping/Products/Product') T(c)

and changed my WHERE statement to:

   WHERE (c.value('(SKU)[1]', 'varchar(10)')='GoodSKU')

Then, I changed the rest of the nodes from a c.value....

   c.value('(Billing/NameParts/FirstName)[1]', 'varchar(50)'),

to a query:

   c.query('../../../Billing/NameParts/FirstName').value('.', 'varchar(25)'),

Finally, I used SUBSTRING and CHARINDEX to extract the values from the CustomerInfo field.

I know I kinda did it on my own, but still.. you pointed me on the right direction and I am grateful for it.
0

Featured Post

Efficient way to get backups off site to Azure

This user guide provides instructions on how to deploy and configure both a StoneFly Scale Out NAS Enterprise Cloud Drive virtual machine and Veeam Cloud Connect in the Microsoft Azure Cloud.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Introduction: When running hybrid database environments, you often need to query some data from a remote db of any type, while being connected to your MS SQL Server database. Problems start when you try to combine that with some "user input" pass…
Browsing the questions asked to the Experts of this forum, you will be amazed to see how many times people are headaching about monster regular expressions (regex) to select that specific part of some HTML or XML file they want to extract. The examp…
This tutorial gives a high-level tour of the interface of Marketo (a marketing automation tool to help businesses track and engage prospective customers and drive them to purchase). You will see the main areas including Marketing Activities, Design …
Two types of users will appreciate AOMEI Backupper Pro: 1 - Those with PCIe drives (and haven't found cloning software that works on them). 2 - Those who want a fast clone of their boot drive (no re-boots needed) and it can clone your drive wh…

786 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question