Signed-off-by: Kai Kreuzer <kai@openhab.org> |
||
---|---|---|
.. | ||
readme.md |
readme.md
id | label | title | type | description | since | install |
---|---|---|---|---|---|---|
xpath | XPath | XPath - Transformation Services | transform | Transforms an [XML](https://www.w3.org/XML/) input using an [XPath](https://www.w3.org/TR/xpath/#section-Expressions) expression. | 2x | auto |
{% include base.html %}
XPath Transformation Service
Transforms an XML input using an XPath expression.
Examples
Basic Example
Given a retrieved XML
Input XML
<?xml version="1.0" encoding="UTF-8"?>
<PTZStatus version="2.0" >
<AbsoluteHigh>
<elevation>0</elevation>
<azimuth>450</azimuth>
<absoluteZoom>10</absoluteZoom>
</AbsoluteHigh>
</PTZStatus>
The XPath /PTZStatus/AbsoluteHigh/azimuth/text()
returns the document
450
Advanced Example
Given a retrieved XML (e.g. from an HIK Vision device with the namespace xmlns="http://www.hikvision.com/ver20/XMLSchema"
):
Input XML
<?xml version="1.0" encoding="UTF-8"?>
<PTZStatus version="2.0" xmlns="http://www.hikvision.com/ver20/XMLSchema">
<AbsoluteHigh>
<elevation>0</elevation>
<azimuth>450</azimuth>
<absoluteZoom>10</absoluteZoom>
</AbsoluteHigh>
</PTZStatus>
A simple xpath query to fetch the Azimut value does not work as it does not address the namespace.
There are two ways to address the namespace.
- Simple path which may not work in complex XML.
- With full qualified path.
The XPath
[name()='PTZStatus']/*[name()='AbsoluteHigh']/*[name()='azimuth']/
/*[local-name()='PTZStatus' and namespace-uri()='http://www.hikvision.com/ver20/XMLSchema']/*[local-name()='AbsoluteHigh' and namespace-uri()='http://www.hikvision.com/ver20/XMLSchema']/*[local-name()='azimuth' and namespace-uri()='http://www.hikvision.com/ver20/XMLSchema']
returns
<azimuth>450</azimuth>
In Setup
.items
String Temperature_xml "Temperature [XPATH(/*[name()='PTZStatus']/*[name()='AbsoluteHigh']/*[name()='azimuth']/):%s °C]" {...}
Number Temperature "Temperature [%.1f °C]"
.rules
rule "Convert XML to Item Type Number"
when
Item Temperature_xml changed
then
// use the transformation service to retrieve the value
// Simple
val mytest = transform("XPATH", "/*[name()='PTZStatus']
/*[name()='AbsoluteHigh']
/*[name()='azimuth']
/text()",
Temperature_xml.state.toString )
// Fully qualified
val mytest = transform("XPATH", "/*[local-name()='PTZStatus' and namespace-uri()='http://www.hikvision.com/ver20/XMLSchema']
/*[local-name()='AbsoluteHigh' and namespace-uri()='http://www.hikvision.com/ver20/XMLSchema']
/*[local-name()='azimuth' and namespace-uri()='http://www.hikvision.com/ver20/XMLSchema']
/text()",
Temperature_xml.state.toString )
// post the new value to the Number Item
Temperature.postUpdate( newValue )
end
Now the resulting Number can also be used in the label to change the color or in a rule as value for comparison.
Further Reading
- An introduction to XPath at W3School
- A informative explanation of common mistakes.
- Online validation tools like this to check the syntax.