declare namespace cat = "http://www.iro.umontreal.ca/lapalme/wine-catalog";
(: to produce legal and validable XHTML ... :)
declare option saxon:output "method=xml";
declare option saxon:output "doctype-public=-//W3C//DTD XHTML 1.0 Strict//EN";
declare option saxon:output "doctype-system=http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd";
declare option saxon:output "indent=yes";
declare variable $GoogleStart := "http://www.google.com/search?q=";
declare function local:root($cellar-book){
<html>
<head><title>Cellar of {data($cellar-book/owner/name)}</title></head>
<body>
{local:cellar-book($cellar-book)}
</body>
</html>
};
declare function local:cellar-book($cellar-book){
<h1>Cellar of {data($cellar-book/owner/name)}</h1>,
<table border="1">
<tr>
<th>Personal address</th>
<th>Cellar address</th>
</tr>
<tr><td>
{for $e in $cellar-book/owner/*[position()>1]
return (data($e),<br/>)}
</td>
<td>{for $e in $cellar-book/location/*
return (data($e),<br/>)}
</td>
</tr>
</table>,
<p/>,
local:cellar($cellar-book/cellar,$cellar-book/cat:wine-catalog)
};
declare function local:cellar($cellar,$catalog){
<table border="1">
<tr>{
for $t in ("Code","Name","Purchase Date","Rating","Nb Bottles")
return <th>{$t}</th>}
</tr>{
for $w in $cellar/wine
order by $w/@code ascending
return local:wine($w,$catalog)}
<tr>
<td colspan="3">Estimated value</td>
<td align="right">{
(: compute the estimated value of the cellar :)
sum (for $w in $cellar/wine,
$codeInCat in $catalog/cat:wine/@code
where $codeInCat = $w/@code
return $w/quantity * $codeInCat/../cat:price)}
</td>
<td align="right">{
(: compute the total number of bottles :)
sum($cellar/wine/quantity)}
</td>
</tr>
</table>,
(: put comment section if at least one comment appears :)
if (count($cellar/wine/comment)>0)
then (
<h3>Comments</h3>,
<p>{for $c in $cellar/wine/comment
order by $c/../@code ascending
return local:comment($c)}
</p>
) else ()
};
declare function local:wine($wine,$catalog){
let $code := $wine/@code
return
<tr>
<td>{substring($code,2)}</td>
<td>{local:nameAndUrl($catalog/cat:wine[@code=$code])}</td>
<td align="right">{data($wine/purchaseDate)}</td>
<td align="center">{substring('*****',1,
if ($wine/rating/@stars) then $wine/rating/@stars else 0)}
</td>
<td align="right">{data($wine/quantity)}</td>
</tr>
};
declare function local:nameAndUrl($wine){
element a {
attribute href{concat($GoogleStart,encode-for-uri($wine/@name))},
data($wine/@name)
}
};
declare function local:comment($comment){
data($comment/../@code),':',local:bold($comment),<br/>
};
declare function local:bold($mixed-content){
for $child in $mixed-content/node()
return if ($child instance of element() and local-name($child)="bold")
then element b{data($child)}
else $child
};
(: change the namespace of a subtree starting at an element
adapted from Priscilla Walmsley, XQuery, O'Reilly, p. 258 :)
declare function local:change-element-ns-deep($element,$new-ns){
element {QName($new-ns,local-name($element))} {
$element/@*,
for $child in $element/node()
return if ($child instance of element())
then local:change-element-ns-deep($child,$new-ns)
else $child
}
};
(: put the whole tree in the XHTML namespace :)
local:change-element-ns-deep(
local:root(/cellar-book),
"http://www.w3.org/1999/xhtml")