Get attribute value by passing node name dynamically in Xpath - xpath

One of the job pulled the files and wrote the data as shown below.
<Data>
<rootDirectory>home</rootDirectory>
<time>20160330124434437</time>
<STE_Document1 filename="REPORT_20160328.csv"/>
<STE_Document2 filename="REPORT_20160328_2.csv"/>
<STE_Document3 filename="REPORT_20160328_3.csv"/>
<STE_DocumentCount>3</STE_DocumentCount>
<DcNbr>1</DcNbr>
</Data>
I have used the xpath statement to retrieve the attribute value filename from First node.
string(/Data/STE_Document1/#filename)
Instead of hardcoding the node name STE_Document1 in xpath , is there a way to provide the trailing number for the node dynamically?
I have loop counter /DcNbr within the job I can use for the trailing number.
I tried
string(/Data/*[starts-with(local-name(), 'STE')][position=1]/#filename)
but it is returning blank.

Related

VB NET XPath won't select a node based on a value

I have a node on an XML file for which I need to select. To select, I have to look at one of the element's value. Once selected, I will then arrange for the entire node to be deleted from the file.
We have a framework that deals with the selecting of nodes however I currently receive the following error: Expression must evaluate to a node-set.
All the framework does is takes in the XMLElement and XPath, and uses what looks to be a defined function named .selectNode(xPath) to find the node. This is what throws the above error.
My XML Data set(which is the XMLElement) looks like this:
<topParent value1="a" value2 = "b">
<att1 value3="c" value4 = "d">
<myline data="e" moredata="f" />
<myline data="g" moredata="h" />
</att1>
</topParent>
and my xPath for selecting looks like : //myline/[#moredata='h']
The idea is to select "myline" node when "moreData" equals h
I've only come across XPath in the last few hours but I can't see why this node isn't being selected.
You shouldn't put a slash before a predicate. It's wrong syntax.
Just use
//myline[#moredata='h']
to select all the myline elements which satisfy the condition.

Get all the child elements of parent node using xpath expression OSB

I am using OSB and have one long XML containing parent and child node.
This is my XML
<XML>
<RefreshLaborApproval2RSP xmlns:XPathFunction="http://www.oracle.com/XSL/Transform/java/mol.prc.labourapproval.XPathFunction" xmlns:tsd="http://namespaces.softwareag.com/tamino/TaminoSchemaDefinition">
<ERRORCODE>
<VALUE>dfdfdf</VALUE>
</ERRORCODE>
<LABORRECORDS>
<LABORNAT>
<VALUE>569</VALUE>
</LABORNAT>
</LABORRECORDS>
<LABORRECORDS>
<LABORNAT>
<VALUE>218</VALUE>
</LABORNAT>
</LABORRECORDS>
</RefreshLaborApproval2RSP>
</XML>
When I use expression XML/* its gives me the whole XML from <RefreshLaborApproval2RSP> to </RefreshLaborApproval2RSP> and kept the same in one variable called xmlparentNode.
And then when I use $xmlparentNode/LABORRECORDS then I get only istLABORRECORDS child element like below.
<LABORRECORDS>
<LABORNAT>
<VALUE>569</VALUE>
</LABORNAT>
</LABORRECORDS>
But I want all <LABORRECORDS> child elements.
I dont know what exacly you want achieve, but you can:
Assign variable xmlparentNode,
Use For Each for example:
a) For Each Variable: Laborrecords
b) XPath: ./LABORRECORDS
c) In Variable: xmlparentNode
d) Index Variable: index
e) Count Variable: count
And then inside For Each do Assign expression: $Laborrecords in variable to get first value, then second.
Do some inserts or something with it.
I do not know if this will solve your problem.
The XML expression that you are using is right.
If the XML elements are very long and you are using variable window (during debugging) to see the element returned, there could be a possible chance to data loss.

Extract a specific node from an XML file

I want to extract only the body node/tag from an XML file using doc.xpath in Ruby
The node to extract from the XML file:
<wcm:element name="Body"><p>A new study suggests that <a href="ssNODELINK/SmokingAndCancer">tobacco</a> companies may be using online video portals, such as YouTube, to get around advertising restrictions and market their products to young people.</p>
</wcm:element>
I have tried the following:
page_content = doc.xpath("/wcm:root/wcm:element").inner_text
But this extracts every node everything
Then I tried this:
page_content = doc.xpath("/wcm:root/wcm:element/Body")
But does not work.
Anyone has any suggestions how to extract exactly the body section of an XML file using doc.xpath in Ruby?
I'm not 100% certain I've understood what you mean but… let's not let that stop us. You want to get the content of a particular node from the input. Your first XPath statement:
/wcm:root/wcm:element
is extracting every element with name wcm:element that is a child of the wcm:root element which is the root element.
Your second:
/wcm:root/wcm:element/Body
is similar but looks for elements with name Body which are children of the wcm:element.
What you need to is to get the values of the wcm:element element where the attribute name is set to the value Body. You access attributes in XPath by prefixing them with an # sign and to express a where condition you use [...] - a predicate. You XPath statement needs to be:
/wcm:root/wcm:element[#name = 'Body']
I'm assuming that your XPath execution environment is fine the namespace prefixes (wcm) because you say that your first query returned content.

Get node text only if contain an attribute?

XPath problem.
I have these nodes:
[...]
<videos>
<video timestamp="201204271112">myVideo.avi</video>
<video>myVideo.avi</video>
<video timestamp="201204271113">myVideo.avi</video>
<video>myVideo.avi</video>
<video>myVideo.avi</video>
</videos>
<photos>
<photo timestamp="201204271112">myphoto.avi</video>
<photo>myphoto.avi</video>
<photo timestamp="201204271113">aphoto.avi</video>
<photo>myphoto.avi</video>
<photo>myphoto.avi</video>
</photos>
[...]
How can i get only node text that contains timestamp attribute?
I tried
//#timestamp
it returns ALL timestamps attribute only. And the text?
How can make a query that include all two conditions? AND condition.
Something like this:
//#text and //#timestamps
to get only
201204271112 - myVideo.avi
201204271113 - myVideo.avi
201204271113 - aphoto.avi
excluding other ones?
thanks.
How can i get only node text that contains timestamp attribute?
Could you mean //*[#timestamp]/text()? That selects all text nodes whose parents have the timestamp attribute.
The conditions are in XPaths, too (i.e. //video[#timestamp and text()] selects all video nodes that have both timestamp and some text nodes).
What you probably meant is a node-set union used with symbol |. To get both the timestamps and the text nodes, you'll need two queries unioned together: //#timestamp | //*[#timestamp]/text() gets all timestamps and all their text nodes. However, I don't think you can get it nicely aligned (there will be all timestamps first, then all text nodes).
You can try either iterating one by one with some kind of for loop and get both the timestamp and the text node via position, or you can just get all nodes that have a timestamp and dig their text out of them later (which is a preffered way).
The spec is a surprisingly good read on this.
You can match on attributes:
//video[#timestamp]/text()
//video = matches a node with name video anywhere in the treee
[#timestamp] is a predicate, meaning the node has to have this attribute
text() selects all text node children of the current node

XPath check for non-existing node

Im having a bit of trouble finding the right XPath syntax to check if a particular node in my XML exists. I'm only allowed to use XPath (so no XSL or something else like that, it has to be a pure XPath expression syntax).
I have an XML and it has a node Filename but it doesn't exist in every case. When the filename isn't specified, my LiveCycle proces will use a different route to fill in the filename. But how do I check if the Filename node exists?
Similar to count but maybe more direct depending of what you want is the function boolean
boolean(//Filename)
This returns true if "Filename" node exist and false if not.
You can use the count function - passing in the path of the nodes you are checking.
If they do not exist, then the value of count will be 0:
count(//Filename) = 0
Suppose you have the following XML document:
<top>
<function>
<filenamex>c:\a\y\z\myFile.xml</filenamex>
<default>Default.xml</default>
</function>
</top>
then this XPath expression selects either the filename element when it's present or the default element when no filename element is specified:
(/*/function/filename
|
/*/function/default
)
[1]
The shortest way to check if the filename element exists is:
/*/function/filename
So the first XPath expression could be re-written in the equivalent (but somewhat longer):
/*/function/filename
|
/*/function/default[not(/*/function/filename)]
Given the example Xml from another answer
<top>
<function>
<filenamex>c:\a\y\z\myFile.xml</filenamex>
<default>Default.xml</default>
</function>
</top>
To get nodes WITH node "filenamex" use /top/function[filenamex]
To get nodes WITHOUT node "filenamex" use /top/function[not(filenamex)]
I felt it necessary to answer here as the other answers did not work as advertised in XmlSpy

Resources