Issue when using xquery external variables from the command line in BaseX - variables

I have the following query in a XQ file named "consulta.xq"
declare namespace xs = "http://www.w3.org/2001/XMLSchema";
declare variable $word as xs:string+ external;
for $entry in doc("cni_es_cushimariano2008")//e
where $entry//l[matches(., $word)]
return <e>{$entry//r//text()} --> {$entry//l//text()}</e>
My database "cni_es_cushimariano2008" has the following structure/data:
<?xml version="1.0" encoding="UTF-8"?>
<dictionary>
<alphabet>aeiobchjmnñprsty</alphabet>
<section id="main" type="standard">
<!-- cuidarse (de alguien). aamaantsi. -->
<e>
<p>
<l>cuidarse (de alguien)</l>
<r>aamaantsi<s n="verbo intransitivo"/>
<s n="infinitivo"/>
</r>
</p>
</e>
<!-- celoso. aamaantsi. -->
<e>
<p>
<l>celoso</l>
<r>aamaantsi<s n="adjetivo"/>
</r>
</p>
</e>
<!-- traer. aamaantsi. -->
<e>
<p>
<l>traer</l>
<r>aamaantsi<s n="verbo transitivo"/>
<s n="infinitivo"/>
</r>
</p>
</e>
</section>
</dictionary>
I am trying to execute the following command line instruction
$ basex -b$word=celoso consulta.xq
but I don't receive the expected result and receive the following message:
[XPDY0002] No value assigned to $word as xs:string+.
I am not an expert using Basex and XQuery so I will be grateful for any answer that might help me. Thanks in advance.

The $ character presumably is interpreted by your command shell, such that $word does not reach its destination. It might need to be escaped,
$ basex -b\$word=celoso consulta.xq
or even omitted,
$ basex -bword=celoso consulta.xq

Related

workaround for missing let in xpath 2.0?

Let's consider the following xml:
<a>
<b id="1"/>
<b id="2"/>
</a>
I understand that for a single value I can use
for $a in //b[#id=1] return $a
instead of the xpath 3.0 expression
let $a := //b[#id=1] return $a
But how can I put a sequence to the variable using for?
obviously
for $a in //b return $a[2]
will return nothing, so it is not a good replacement for
let $a := //b return $a[2]
I tried to construct a sequence where //b is the first element, and () is the second, and use it, but I could not figure out how to do it.
Use:
for $len in count(/*/b),
$ind in 1 to $len
return
(/*/b)[$ind]
XSLT 2.0 - based verification:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:template match="/">
<xsl:sequence select=
"for $len in count(/*/b),
$ind in 1 to $len
return
(/*/b)[$ind] "/>
</xsl:template>
</xsl:stylesheet>
When this transformation is applied on the provided XML document:
<a>
<b id="1"/>
<b id="2"/>
</a>
the XPath expression is evaluated and the sequence that is the result of this evaluation is output:
<b id="1"/>
<b id="2"/>

Querying an XML-Object in Oracle SQL: getting a value of an attribut by specifying another attribut of the object

I know there are many entries here concerning querying an XML-Object in Oracle SQL. But still, I couldn't find any answer on my question.
I have a SQL table obj with some columns incl. a clob object in the XML format (column is called definition).
I want to extract a concrete value from the clob.
The XML looks like this:
<?xml version="1.0" encoding="UTF-8"?>
<m>
<i n="Status">0</i>
<s n="Description">AmountDifference</s>
<s n="Name">InputvsOutput</s>
<a n="Variables">
<m>
<s n="Name">Formula</s>
<s n="Value">B-A</s>
</m>
<m>
<s n="Name">CriticalDiff</s>
<s n="Value">abs({B} - {A}) < 10</s>
</m>
</a>
</m>
The SQL query should return two values: Description and a Value where Name = CriticalDiff.
The part of SQL query looks like this:
CAST(
CASE WHEN obj.definition is not null then
UTL_I18N.UNESCAPE_REFERENCE(
XMLTYPE(obj.definition).
EXTRACT('//s[#n="Description"]/text()')
.getStringVal() )
END as varchar(200)) as "Rule Expression"
, obj.definition as rule_xml
The CAST block is working fine, but I wonder how to transform the last command in the similar way, so that I get a value by its name (= CriticalDiff).
The difficulty I face is that there are two similar elements (m) with the same attribute names (Name, Value).
Any ideas how I can get a "Value"-attribute from "CriticalDiff" ?
Thanks in advance!
Try:
WITH obj AS (
SELECT q'[<?xml version="1.0" encoding="UTF-8"?>
<m>
<i n="Status">0</i>
<s n="Description">AmountDifference</s>
<s n="Name">InputvsOutput</s>
<a n="Variables">
<m>
<s n="Name">Formula</s>
<s n="Value">B-A</s>
</m>
<m>
<s n="Name">CriticalDiff</s>
<s n="Value">abs({B} - {A}) < 10</s>
</m>
</a>
</m>]' as definition FROM dual
) SELECT
XMLTYPE( obj.definition ).
EXTRACT('//s[#n="Description"]/text()').getStringVal() as Description,
XMLTYPE( obj.definition ).
EXTRACT('//m/s[#n="Name" and text() = "CriticalDiff"]/text()').getStringVal() as Name,
UTL_I18N.UNESCAPE_REFERENCE(XMLTYPE( obj.definition ).
EXTRACT('//m/s[#n="Name" and text() = "CriticalDiff"]/../s[#n="Value"]/text()').getStringVal()) as Value
FROM obj;
DESCRIPTION |NAME |VALUE |
-----------------|-------------|--------------------|
AmountDifference |CriticalDiff |abs({B} - {A}) < 10 |
Another version of xpath that also works:
EXTRACT('//m[s[#n="Name" and text() = "CriticalDiff"]]/s[#n="Value"]/text()').getStringVal()) as Value

PairSet repetition in ttf font GPOS table

I am reading ttf specification and realizing the parser. But I have encountered a problem of parsing 'GPOS' table.
This is the link to GPOS table specification: http://www.microsoft.com/typography/otspec/gpos.htm
It says:
ValueFormat2 applies to the ValueRecord of the second glyph in each pair. ValueRecords for all second glyphs must use ValueFormat2. If ValueFormat2 is set to null, then the second glyph of the pair is the “next” glyph for which a lookup should be performed.
My first question: What would happen when 'ValueFormat2' is 'null'? Is it the same with 'ValueFormat1'? If so, why the spec using different expressions?
Compared with the .ttx file generated by ttx, I find that there are repetitions of PairSet in GPOS section. But my parser couldn't read out such repetitions from ttf binary file. For example: times.ttf on Windows7. File 'time.ttx' has the following items, but my parser reads out 'index 13', then the next group is 'index 16', which means I have missed 'index 14' and 'index 15'. And I don't know why I cannot read out the same result as ttx does.
My second question: Is there anything I have missed from the ttf specification? Which and where are such repetitions explained? Thanks in advance!
<PairSet index="13">
<!-- PairValueCount=2 -->
<PairValueRecord index="0">
<SecondGlyph value="comma"/>
<Value1 XAdvance="-133"/>
</PairValueRecord>
<PairValueRecord index="1">
<SecondGlyph value="period"/>
<Value1 XAdvance="-133"/>
</PairValueRecord>
</PairSet>
<PairSet index="14">
<!-- PairValueCount=2 -->
<PairValueRecord index="0">
<SecondGlyph value="comma"/>
<Value1 XAdvance="-133"/>
</PairValueRecord>
<PairValueRecord index="1">
<SecondGlyph value="period"/>
<Value1 XAdvance="-133"/>
</PairValueRecord>
</PairSet>
<PairSet index="15">
<!-- PairValueCount=2 -->
<PairValueRecord index="0">
<SecondGlyph value="comma"/>
<Value1 XAdvance="-133"/>
</PairValueRecord>
<PairValueRecord index="1">
<SecondGlyph value="period"/>
<Value1 XAdvance="-133"/>
</PairValueRecord>
</PairSet>
<PairSet index="16">
<!-- PairValueCount=1 -->
<PairValueRecord index="0">
<SecondGlyph value="quoteleft"/>
<Value1 XAdvance="-152"/>
</PairValueRecord>
</PairSet>

Tips for finding prefixed tags in python lxml?

I am trying to using lxml's ElementTree etree to find a specific tag in my xml document.
The tag looks as follows:
<text:ageInformation>
<text:statedAge>12</text:statedAge>
</text:ageInformation>
I was hoping to use etree.find('text:statedAge'), but that method does not like 'text' prefix.
It mentions that I should add 'text' to the prefix map, but I am not certain how to do it. Any tips?
Edit:
I want to be able to write to the hr4e prefixed tags.
Here are the important parts of the document:
<?xml version="1.0" encoding="utf-8"?>
<greenCCD xmlns="AlschulerAssociates::GreenCDA" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:hr4e="hr4e::patientdata" xsi:schemaLocation="AlschulerAssociates::GreenCDA green_ccd.xsd">
<header>
<documentID root="18c41e51-5f4d-4d15-993e-2a932fed720a" />
<title>Health Records for Everyone Continuity of Care Document</title>
<version>
<number>1</number>
</version>
<confidentiality codeSystem="2.16.840.1.113883.5.25" code="N" />
<documentTimestamp value="201105300211+0800" />
<personalInformation>
<patientInformation>
<personID root="2.16.840.1.113883.3.881.PI13023911" />
<personAddress>
<streetAddressLine nullFlavor="NI" />
<city>Santa Cruz</city>
<state nullFlavor="NI" />
<postalCode nullFlavor="NI" />
</personAddress>
<personPhone nullFlavor="NI" />
<personInformation>
<personName>
<given>Benjamin</given>
<family>Keidan</family>
</personName>
<gender codeSystem="2.16.840.1.113883.5.1" code="M" />
<personDateOfBirth value="NI" />
<hr4e:ageInformation>
<hr4e:statedAge>9424</hr4e:statedAge>
<hr4e:estimatedAge>0912</hr4e:estimatedAge>
<hr4e:yearInSchool>1</hr4e:yearInSchool>
<hr4e:statusInSchool>attending</hr4e:statusInSchool>
</hr4e:ageInformation>
</personInformation>
<hr4e:livingSituation>
<hr4e:homeVillage>Putney</hr4e:homeVillage>
<hr4e:tribe>Oromo</hr4e:tribe>
</hr4e:livingSituation>
</patientInformation>
</personalInformation>
The namespace prefix must be declared (mapped to an URI) in the XML document. Then you can use the {URI}localname notation to find text:statedAge and other elements. Something like this:
from lxml import etree
XML = """
<root xmlns:text="http://example.com">
<text:ageInformation>
<text:statedAge>12</text:statedAge>
</text:ageInformation>
</root>"""
root = etree.fromstring(XML)
ageinfo = root.find("{http://example.com}ageInformation")
age = ageinfo.find("{http://example.com}statedAge")
print age.text
This will print "12".
Another way of doing it:
ageinfo = root.find("text:ageInformation",
namespaces={"text": "http://example.com"})
age = ageinfo.find("text:statedAge",
namespaces={"text": "http://example.com"})
print age.text
You can also use XPath:
age = root.xpath("//text:statedAge",
namespaces={"text": "http://example.com"})[0]
print age.text
I ended up having to use nested prefixes:
from lxml import etree
XML = """
<greenCCD xmlns="AlschulerAssociates::GreenCDA" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:hr4e="hr4e::patientdata" xsi:schemaLocation="AlschulerAssociates::GreenCDA green_ccd.xsd">
<personInformation>
<hr4e:ageInformation>
<hr4e:statedAge>12</hr4e:statedAge>
</hr4e:ageInformation>
</personInformation>
</greenCCD>"""
root = etree.fromstring(XML)
#root = etree.parse("hr4e_patient.xml")
ageinfo = root.find("{AlschulerAssociates::GreenCDA}personInformation/{hr4e::patientdata}ageInformation")
age = ageinfo.find("{hr4e::patientdata}statedAge")
print age.text

How do I conditionally add an id attribute in TAL (PHPTAL)?

I'm creating a form elements template file in PHPTAL. I would like to be able to OPTIONALLY pass in an id attribute for a field...
So far the code looks like this:
<xml>
<tal:block metal:define-macro="text">
<label tal:condition="php: !isset(hideLabel) || isset(hideLabel) && !hideLabel">${field/label}</label>
<input name="${name}" type="text" value="${field/value}" />
<p tal:condition="exists:field/error">${field/error}</p>
</tal:block>
</xml>
This works as advertised. What I'd like to add is something, like
<input name="${name}" tal:attributes="id exists: id $id | $name" value="${field/value}" />
to allow me to optionally pass in an id from the METAL call...
Should I be doing it differently? I've tried using PHP: isset(id) ? $id : NULL and variations thereof, but just end up with an id="0" in the resultant HTML.
Any ideas?
In case anyone else needs it, one working answer is:
<xml>
<tal:block metal:define-macro="text">
<label tal:condition="not: exists:hideLabel">${field/label}</label>
<input name="${name}" tal:attributes="id id | nothing" type="text" value="${field/value}" />
<p tal:condition="exists:field/error">${field/error}</p>
</tal:block>
</xml>
Where passed in variables are id, name, an array named field, and hideLabel .
Note, that I've also managed to simplify the label test to something which I believe is more idiomatically TAL.
Set VAR at a DIV containing the soon to be used element:
div class="" tal:define="VAR context.property"
div class="" tal:attributes="class python:'grid_8 omega' if VAR else 'grid_8 alpha'"
in PHP:
<div id="contentCenter" tal:attributes="id
php:isset(variable)&&isset(variable.property)?'IDVALUE':NULL">