Skip to content

Instantly share code, notes, and snippets.

@linjunpop
Created November 14, 2012 03:29
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save linjunpop/4070069 to your computer and use it in GitHub Desktop.
Save linjunpop/4070069 to your computer and use it in GitHub Desktop.
XQuery taste
(: return a deep copy of the element and all sub elements :)
declare function local:copy($elements as element()+) as element()+ {
for $element in $elements
return element {node-name($element)}
{$element/@*,
for $child in $element/node()
return
if ($child instance of element())
then local:copy($child)
else $child
}
};
(: return the sorted toc-title :)
declare function local:toc-title($doc) as element()+
{
for $x in $doc//toc-title
order by $x/@locator descending
return $x
};
(: return the toc tree:)
declare function local:toc() as element()+
{
for $x in doc('text')/federal-register/front-matter/toc
return <toc pages="{string-join(data($x/pages), ',')}">{local:copy($x/*)}</toc>
};
(: return subjects :)
declare function local:subject($doc) as element()+
{
for $x in $doc//subject
let $y := data($x/@after_content)
return <subject>{$x/*} {$y}</subject>
};
(: results :)
declare variable $toc := local:toc();
declare variable $toc-title := local:toc-title($toc);
declare variable $subject := local:subject($toc);
$subject
declare variable $doc := doc('text');
(: transform :)
declare function local:dispatch($node as node()) as item()* {
typeswitch($node)
case text() return $node
case element(toc-agency) return local:toc-agency($node)
case element(toc) return local:toc($node)
case element(pages) return local:pages($node)
case element(docent) return local:docent($node)
default return (
element {node-name($node)} {local:passthru($node)}
)
};
declare function local:passthru($nodes as node()) as item()* {
for $node in $nodes/node() return local:dispatch($node)
};
(: functions :)
declare function local:toc($node as element(toc))
{
<toc pages="{string-join(data($node/pages), ',')}">
{local:passthru($node)}
</toc>
};
declare function local:pages($node as element(pages))
{
""
};
declare function local:docent($node as element(docent))
{
for $toc-title in $node/toc-title
return (
local:passthru($node),
$toc-title
)
};
declare function local:toc-agency($node as element(toc-agency))
{
for $x in $node/node()
order by $x/@locator descending
return (
local:passthru($node),
$x
)
};
local:dispatch($doc/node())
declare variable $doc := doc('text');
declare updating function local:rename($selector, $replace)
{
for $node in $selector
return(
rename node $node as $replace
)
};
declare updating function local:update-pages-for-toc()
{
for $toc in $doc//toc
return (
insert node attribute pages {string-join(data($toc/pages), ',')} into $toc,
delete node $toc/pages
)
};
declare updating function local:remove-docent()
{
for $toc-agency in $doc//toc-agency
return (
for $docent in $toc-agency/docent
return (
replace node $docent with $docent/toc-title
)
)
};
declare function local:ordered-toc-agency-children($toc-agency) as element()+
{
for $child in $toc-agency/*
order by $child/@locator descending
return $child
};
declare updating function local:sort-toc-agency-children()
{
for $toc-agency in $doc//toc-agency
let $ordered := local:ordered-toc-agency-children($toc-agency)
return (
replace node $toc-agency with <toc-agency>{$ordered}</toc-agency>
)
};
declare updating function local:main()
{
local:update-pages-for-toc(),
local:remove-docent(),
local:sort-toc-agency-children()
};
local:main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment