473,804 Members | 2,296 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

XmlDocument.Sel ectSingleNode() & namespaces - doesn't work

Hi;

If there are no namespaces this works fine for me. But if the xml has
namespaces, then I get either no node back or an exception.

Here is the sample xml:
<root xmlns="http://www.test.org"
xmlns:sns="http ://www.test.org/sub"
xmlns:mns="http ://www.test.org/mini">
<data>
<items>
<item id="1">
<sns:subItem sid="11">dave</sns:subItem>
<sns:subItem sid="12">thiele n</sns:subItem>
</item>
<item id="2">
<sns:subItem sid="21">shirle y</sns:subItem>
</item>
</items>
<mns:more>dav e thielen</mns:more>
</data>
</root>

1. If I do SelectSingleNod e("/root/data/items/item/@id") - I get no nodes
returned. This is the case if I create an XmlNamespaceMan ager or not.

2. If I do SelectSingleNod e("/root/data/items/item/sns:subItem/@sid") where
I have a namespace qualified node I get:

2a. If there is no XmlNamespaceMan ager I get an exception.

2b. If I add the following code:
XmlNamespaceMan ager context = new XmlNamespaceMan ager(doc.NameTa ble);
context.AddName space("sns", "http://www.test.org/sub");
node = doc.SelectSingl eNode(("/root/data/items/item/sns:subItem/@sid",
context);
Then I get no nodes returned (but at least no exception is thrown).

I tested all of the in XmlSpy and the xpath works there as expected.

So what is going on?

First off, even if I add the namespaces, I still can't get any node
returned. Both those with namespaces and those without evaluate to no nodes.

Second, why does it throw an exception if I don't create a namespace
manager? The namespaces exist in the xml file and by definition, those
mappings should be used. Also, to quote from
http://msdn.microsoft.com/library/de...edprefixes.asp
"If the msbooks namespace was not added to the XmlNamespaceMan ager, and if it
is not in the name table of the document, then an exception is thrown." So
there should be no exception thrown for namespaces that are defined in the
document.

Help please - this makes no sense to me.

--
thanks - dave
Nov 12 '05 #1
19 16225
Hi Dave,

First of all, I would like to confirm my understanding of your issue. From
your description, I understand that you are trying to use SelectSingleNod e
to get the attribute. If there is any misunderstandin g, please feel free to
let me know.

Since the nodes are under the default namespace, SelectSingleNod e require
us to specify the namespace for each node in the Xpath expression including
the default namespace. You can get /root/data/items/item/@id with the
following piece of code.

XmlDocument doc =new XmlDocument();
doc.LoadXml(s);
XmlNamespaceMan ager nsmgr = new XmlNamespaceMan ager(doc.NameTa ble);
nsmgr.AddNamesp ace("d", "http://www.test.org");
nsmgr.AddNamesp ace("sns", "http://www.test.org/sub");
nsmgr.AddNamesp ace("mns", "http://www.test.org/mini");
XmlNode node = doc.SelectSingl eNode("//d:root/d:data/d:items/d:item/@id",
nsmgr);

Also, to get to /root/data/items/item/sns:subItem/@sid, Please use the
following code.

XmlNode node =
doc.SelectSingl eNode("//d:root/d:data/d:items/d:item/sns:subItem/@sid",
nsmgr);

HTH.

Kevin Yu
=======
"This posting is provided "AS IS" with no warranties, and confers no
rights."

Nov 12 '05 #2
Hello;

My problem is that I am not hardcoding the xpath - I have to accept what the
user types in. And I have to accept any legal xpath and it is legal to enter
it with no namespace on the nodes that are in the default namespace.

How can I get this to handle any legal xpath string? (In other words, to
work the same way XmlSpy, dom4j, XSLT, and every other program that accepts
xpath works.)

--
thanks - dave
"Kevin Yu [MSFT]" wrote:
Hi Dave,

First of all, I would like to confirm my understanding of your issue. From
your description, I understand that you are trying to use SelectSingleNod e
to get the attribute. If there is any misunderstandin g, please feel free to
let me know.

Since the nodes are under the default namespace, SelectSingleNod e require
us to specify the namespace for each node in the Xpath expression including
the default namespace. You can get /root/data/items/item/@id with the
following piece of code.

XmlDocument doc =new XmlDocument();
doc.LoadXml(s);
XmlNamespaceMan ager nsmgr = new XmlNamespaceMan ager(doc.NameTa ble);
nsmgr.AddNamesp ace("d", "http://www.test.org");
nsmgr.AddNamesp ace("sns", "http://www.test.org/sub");
nsmgr.AddNamesp ace("mns", "http://www.test.org/mini");
XmlNode node = doc.SelectSingl eNode("//d:root/d:data/d:items/d:item/@id",
nsmgr);

Also, to get to /root/data/items/item/sns:subItem/@sid, Please use the
following code.

XmlNode node =
doc.SelectSingl eNode("//d:root/d:data/d:items/d:item/sns:subItem/@sid",
nsmgr);

HTH.

Kevin Yu
=======
"This posting is provided "AS IS" with no warranties, and confers no
rights."

Nov 12 '05 #3
try out SelectSingleNod e("//root/data/items/item[@id='1']")
SelectSingleNod e("//root/data/items/item[@id='2']")

Harry

"David Thielen" wrote:
Hi;

If there are no namespaces this works fine for me. But if the xml has
namespaces, then I get either no node back or an exception.

Here is the sample xml:
<root xmlns="http://www.test.org"
xmlns:sns="http ://www.test.org/sub"
xmlns:mns="http ://www.test.org/mini">
<data>
<items>
<item id="1">
<sns:subItem sid="11">dave</sns:subItem>
<sns:subItem sid="12">thiele n</sns:subItem>
</item>
<item id="2">
<sns:subItem sid="21">shirle y</sns:subItem>
</item>
</items>
<mns:more>dav e thielen</mns:more>
</data>
</root>

1. If I do SelectSingleNod e("/root/data/items/item/@id") - I get no nodes
returned. This is the case if I create an XmlNamespaceMan ager or not.

2. If I do SelectSingleNod e("/root/data/items/item/sns:subItem/@sid") where
I have a namespace qualified node I get:

2a. If there is no XmlNamespaceMan ager I get an exception.

2b. If I add the following code:
XmlNamespaceMan ager context = new XmlNamespaceMan ager(doc.NameTa ble);
context.AddName space("sns", "http://www.test.org/sub");
node = doc.SelectSingl eNode(("/root/data/items/item/sns:subItem/@sid",
context);
Then I get no nodes returned (but at least no exception is thrown).

I tested all of the in XmlSpy and the xpath works there as expected.

So what is going on?

First off, even if I add the namespaces, I still can't get any node
returned. Both those with namespaces and those without evaluate to no nodes.

Second, why does it throw an exception if I don't create a namespace
manager? The namespaces exist in the xml file and by definition, those
mappings should be used. Also, to quote from
http://msdn.microsoft.com/library/de...edprefixes.asp
"If the msbooks namespace was not added to the XmlNamespaceMan ager, and if it
is not in the name table of the document, then an exception is thrown." So
there should be no exception thrown for namespaces that are defined in the
document.

Help please - this makes no sense to me.

--
thanks - dave

Nov 12 '05 #4


David Thielen wrote:

My problem is that I am not hardcoding the xpath - I have to accept what the
user types in. And I have to accept any legal xpath and it is legal to enter
it with no namespace on the nodes that are in the default namespace.


While an XPath expression
element-name
is syntactically correct it always selects only elements with the
element name 'element-name' in no namespace, if you want to select
elements in a namespace then you need to bind a prefix to the namespace
URI and use that prefix in the XPath expression, no change to the XML
document is needed for that, see also
<http://www.faqts.com/knowledge_base/view.phtml/aid/34022/fid/616>

--

Martin Honnen --- MVP XML
http://JavaScript.FAQTs.com/
Nov 12 '05 #5
Hi;

Tried - it didn't work.

--
thanks - dave
"Harry_Crow " wrote:
try out SelectSingleNod e("//root/data/items/item[@id='1']")
SelectSingleNod e("//root/data/items/item[@id='2']")

Harry

"David Thielen" wrote:
Hi;

If there are no namespaces this works fine for me. But if the xml has
namespaces, then I get either no node back or an exception.

Here is the sample xml:
<root xmlns="http://www.test.org"
xmlns:sns="http ://www.test.org/sub"
xmlns:mns="http ://www.test.org/mini">
<data>
<items>
<item id="1">
<sns:subItem sid="11">dave</sns:subItem>
<sns:subItem sid="12">thiele n</sns:subItem>
</item>
<item id="2">
<sns:subItem sid="21">shirle y</sns:subItem>
</item>
</items>
<mns:more>dav e thielen</mns:more>
</data>
</root>

1. If I do SelectSingleNod e("/root/data/items/item/@id") - I get no nodes
returned. This is the case if I create an XmlNamespaceMan ager or not.

2. If I do SelectSingleNod e("/root/data/items/item/sns:subItem/@sid") where
I have a namespace qualified node I get:

2a. If there is no XmlNamespaceMan ager I get an exception.

2b. If I add the following code:
XmlNamespaceMan ager context = new XmlNamespaceMan ager(doc.NameTa ble);
context.AddName space("sns", "http://www.test.org/sub");
node = doc.SelectSingl eNode(("/root/data/items/item/sns:subItem/@sid",
context);
Then I get no nodes returned (but at least no exception is thrown).

I tested all of the in XmlSpy and the xpath works there as expected.

So what is going on?

First off, even if I add the namespaces, I still can't get any node
returned. Both those with namespaces and those without evaluate to no nodes.

Second, why does it throw an exception if I don't create a namespace
manager? The namespaces exist in the xml file and by definition, those
mappings should be used. Also, to quote from
http://msdn.microsoft.com/library/de...edprefixes.asp
"If the msbooks namespace was not added to the XmlNamespaceMan ager, and if it
is not in the name table of the document, then an exception is thrown." So
there should be no exception thrown for namespaces that are defined in the
document.

Help please - this makes no sense to me.

--
thanks - dave

Nov 12 '05 #6
Hi;

There are a couple of things that don't strike me as right about this.

First, these xpath queries do work in XmlSpy and when using dom4j. And I
understand the difference between no namespace and default namespace - but
the 1.0 spec is a bit unclear on exactly what this means in practice. But it
seems to me that this should work in .NET since it works elsewhere.

Second, the namespaces are defined in the xml file. So why do they need to
be set again using XmlNamespaceMan ager.AddNamespa ce()? It should be able to
get those when parsing the xml file.

In my case I can't force these things because I have to handle xml files and
xpath statements given to me by a user in my app. So I can't create a
hard-coded work-around for this.

???

--
thanks - dave
"Martin Honnen" wrote:


David Thielen wrote:

My problem is that I am not hardcoding the xpath - I have to accept what the
user types in. And I have to accept any legal xpath and it is legal to enter
it with no namespace on the nodes that are in the default namespace.


While an XPath expression
element-name
is syntactically correct it always selects only elements with the
element name 'element-name' in no namespace, if you want to select
elements in a namespace then you need to bind a prefix to the namespace
URI and use that prefix in the XPath expression, no change to the XML
document is needed for that, see also
<http://www.faqts.com/knowledge_base/view.phtml/aid/34022/fid/616>

--

Martin Honnen --- MVP XML
http://JavaScript.FAQTs.com/

Nov 12 '05 #7
Hi Dave,

I'm afraid this is by design in .NET framework. The XmlSpy uses a standard
way in the spec, but in the .NET Xml, we have its own implementation of the
Xpath query.

The XmlNamespaceMan ager object is designed to serve as a collection of
namespace definitions. It is used by the .NET Framework XML processors to
resolve and manage the scope of namespaces used in XML documents. So you
must use a System.Xml.XmlN amespaceManager object to provide the required
namespace resolution and scope management support.

You can check the following KB articles for more information.

http://support.microsoft.com/?id=313828
http://support.microsoft.com/?id=316913

Kevin Yu
=======
"This posting is provided "AS IS" with no warranties, and confers no
rights."

Nov 12 '05 #8
Hi;

Ok - this seems to be required. But it's nuts - this does not match the W3C
standard as far as I can tell. Especially ignoring the namespace settings in
the xml file.

Does anyone have any code to work around this? There have to be others who
have parsed the xml file to pull out the namespace declarations and declare
them programatically to get the standard xpath functionality.

--
thanks - dave
"Kevin Yu [MSFT]" wrote:
Hi Dave,

I'm afraid this is by design in .NET framework. The XmlSpy uses a standard
way in the spec, but in the .NET Xml, we have its own implementation of the
Xpath query.

The XmlNamespaceMan ager object is designed to serve as a collection of
namespace definitions. It is used by the .NET Framework XML processors to
resolve and manage the scope of namespaces used in XML documents. So you
must use a System.Xml.XmlN amespaceManager object to provide the required
namespace resolution and scope management support.

You can check the following KB articles for more information.

http://support.microsoft.com/?id=313828
http://support.microsoft.com/?id=316913

Kevin Yu
=======
"This posting is provided "AS IS" with no warranties, and confers no
rights."

Nov 12 '05 #9
David Thielen wrote:
First, these xpath queries do work in XmlSpy and when using dom4j.
That means XmlSpy and Dom4J are seriously broken. Your queries must
return nothing on your XML as per XPath 1.0 spec.
And I
understand the difference between no namespace and default namespace - but
the 1.0 spec is a bit unclear on exactly what this means in practice. But it
seems to me that this should work in .NET since it works elsewhere.
It doesn't work with any conformant XSLT processor I'm aware. Actually
it works as expected - returns nothing. That's the most FAQ ever with
XPath. Read "XML Namespaces and How They Affect XPath and XSLT" at
http://msdn.microsoft.com/library/de...ml05202002.asp

Second, the namespaces are defined in the xml file. So why do they need to
be set again using XmlNamespaceMan ager.AddNamespa ce()? It should be able to
get those when parsing the xml file.
Because in XML you might define zillion of different namespaces with or
without clashing prefixes and so when you query for an element you must
say explicitly which namespace you are interested in. Take a look at
this XML:
<foo xmlns="urn:bar" >
<foo xmlns="urn:foo"/>
</foo>

Which foo element should be selected by "//foo" query? The answer as per
XPath 1.0 spec is - none, because "foo" in XPath 1.0 means element in no
namespace.
In my case I can't force these things because I have to handle xml files and
xpath statements given to me by a user in my app. So I can't create a
hard-coded work-around for this.


Then your app is broken by design. When user query XML she must be able
to define mapping between namespace prefixes used in a query and
namespace URIs.

--
Oleg Tkachenko [XML MVP, MCAD]
http://blog.tkachenko.com
Nov 12 '05 #10

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

1
2538
by: Station Media | last post by:
Hi, here my problem, i use stored procedure in ACCESS database(latest version), and i would like to use this procedure but it doesnt work, do you know why ? Procedure: PARAMETERS MyField Text ( 255 ); SELECT DISTINCT MyField AS Result FROM tb_Client;
3
7226
by: Clouds | last post by:
Hi ! How do I add the dynamic event handler for a dropdownlist present in the itemtemplate of a datalist !! I am doing it in the itemdatabound event of the datalist but it doesnt work... I am also setting the autopostback property to true for the dropdown list and it works but the handler doesnt get invoked at runtime... I have to do it in itemdatabound becaz whether to add the handler or not is driven based on the information which i...
4
4577
by: Daniel | last post by:
Is it possible to use regular expressions inside of an xpath statement executed by System.Xml.XmlDocument.SelectSingleNode() ? string sdoc = "<foo><bar a='1'/><bar a='2'/></foo>"; System.Xml.XmlDocument pdoc = new System.Xml.XmlDocument(); pdoc.LoadXml(sdoc); System.Xml.XmlNode pnode = pdoc.SelectSingleNode("//foo/bar/matches(.,'\\d')"); string foo = pnode.InnerText; int i23 = 23 + 23;
0
1650
by: Juna | last post by:
I have been working in vs2003, but now started to work in vs2005 but the problem, I have simple web application not website, which work i mean open in browser when we press F5 or run the application by pressing run button. but it doesnt work when we type the path directly in the browser's address bar eg. http://localhost/testapplicationdefault.aspx error it gives is "COULD NOT LOAD testapplication._default". IN default.aspx. While in...
1
2087
Digital Don
by: Digital Don | last post by:
I am writing a program for Peg solitaire... To check for no repetition of previous states I use a Set for storage of Board states.. The pronblem is when I declare the set as type char i.e. set <char> open it doesnt take any char values into it and says cannot convert char to const char... I wonder why is it converting char to const char when I have declared that it shud be of type char...It doesnt work with int either,.. Please help...
3
2986
by: jx2 | last post by:
hi guys i would appriciate your coments on this code - when i ran it for the very first time it doesnt see @last = LAST_INSERT_ID() but when i ran it next time it read it properly i need to know it imiedietely after i insert value into session1... is there any other way to do it? insert into 2 tables at the same time ...? if(!($sessid)){ session_register('sessid'); mysql_query("insert into session1 set sessid=null,
1
1601
by: Dany13 | last post by:
hi all. i using some text box for input value and some localvarible for passing this data to dataset . give instance for correct row of dataset and data in data table . use one gird view for showing curent data in dataset . in end i am calling update metod to insert data in sql database but this metod doesnt work correctly. at all doesnt work. but givenot any error . fill data from my database (work propebly) ...
20
2883
by: Hush | last post by:
Hi, The following code works fine in IE7 but FF returns with an error: Access denied to achieve the property Element.firstChild. In this line: nodes = xmlDoc.documentElement.childNodes; My code:
0
9714
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However, people are often confused as to whether an ONU can Work As a Router. In this blog post, we’ll explore What is ONU, What Is Router, ONU & Router’s main usage, and What is the difference between ONU and Router. Let’s take a closer look ! Part I. Meaning of...
0
9594
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
10346
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that captivates audiences and drives business growth. The Art of Business Website Design Your website is...
1
10347
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
0
9173
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then launch it, all on its own.... Now, this would greatly impact the work of software developers. The idea...
1
7635
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new presenter, Adolph Dupré who will be discussing some powerful techniques for using class modules. He will explain when you may want to use classes instead of User Defined Types (UDT). For example, to manage the data in unbound forms. Adolph will...
0
6863
by: conductexam | last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and then checking html paragraph one by one. At the time of converting from word file to html my equations which are in the word document file was convert into image. Globals.ThisAddIn.Application.ActiveDocument.Select();...
0
5531
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
2
3832
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.