fixed storing the value_meaning_identifier to reflect correctly in the data_element_summary template Each value meaning stores the correct corresponding identifier to conceptual_domain

xquery version "1.0";

(: ~
 : Module Name:             new value domain webpage and XQuery
 :
 : Module overview          Creates and value domain and displays list
 :)

(:~
 :    @author Rakesh Dhaval
 :    @version 0.1
~ :)

  import module namespace
  lib-forms="http://www.cagrid.org/xquery/library/forms"
  at "../edit/m-lib-forms.xquery";

  import module namespace
  lib-util="http://www.cagrid.org/xquery/library/util"
  at "../library/m-lib-util.xquery";

  import module namespace
  lib-rendering="http://www.cagrid.org/xquery/library/rendering"
  at "../web/m-lib-rendering.xquery";

  import module namespace
    lib-make-admin-item="http://www.cagrid.org/xquery/library/make-admin-item"
    at "../edit/m-lib-make-admin-item.xquery";

  import module namespace
   administered-item="http://www.cagrid.org/xquery/library/administered-item"
   at "../library/m-administered-item.xquery";

declare namespace openMDR = "http://www.cagrid.org/schema/openMDR";
declare namespace ISO11179= "http://www.cagrid.org/schema/ISO11179";
declare namespace session="http://exist-db.org/xquery/session";
declare namespace response="http://exist-db.org/xquery/response";
declare namespace exist = "http://exist.sourceforge.net/NS/exist";
declare namespace util="http://exist-db.org/xquery/util";

declare function local:value_domain(
   $reg-auth as xs:string,
   $administrative-note as xs:string,
   $administrative-status as xs:string,
   $administered-by as xs:string,
   $submitted-by as xs:string,
   $registered-by as xs:string,
   $context-ids as xs:string*,
   $country-identifiers as xs:string*,
   $language-identifiers as xs:string*,
   $names as xs:string*,
   $definitions as xs:string*,
   $sources as xs:string*,
   $preferred as xs:string?,
   $conceptual_domain_id as xs:string?,
   $enum_datatype as xs:string?,
   $enum_uom as xs:string?,
   $values as xs:string*
   ) as xs:boolean
{
   let $version := '0.1'
   let $data-identifier := lib-forms:generate-id()
   let $new-identifier := concat($reg-auth, '-', $data-identifier, '-', $version)
   let $doc-name := concat($new-identifier,'.xml')
   let $concept_domain := lib-util:mdrElement("conceptual_domain",$conceptual_domain_id)
   let $value_meaning-identifier  := data($concept_domain//openMDR:value_meaning_identifier)

   let $content := (
            lib-make-admin-item:administration-record($administrative-note,$administrative-status,'Recorded'),
            lib-make-admin-item:custodians($administered-by,$registered-by,$submitted-by),
            lib-make-admin-item:havings(
                    $context-ids,
                    $country-identifiers,
                    $language-identifiers,
                    $names,
                    $definitions,
                    $preferred,
                    $sources),

             for $meaning at $pos in $concept_domain//openMDR:value_meaning_description
                    return (
                       element openMDR:containing {
                         attribute permissible_value_identifier {lib-forms:generate-id()},
                         element openMDR:permissible_value_begin_date {current-date()},
                         element openMDR:value_item {$values[$pos]},
                         element openMDR:contained_in {$value_meaning-identifier[$pos]}
                       }
             ),
            element openMDR:representing {$conceptual_domain_id},
            element openMDR:value_domain_datatype {$enum_datatype},
            element openMDR:value_domain_unit_of_measure {$enum_uom}

    )

   (: compose the document :)
   let $document := (
     if($values > '' ) then (
      element openMDR:Enumerated_Value_Domain {
            attribute item_registration_authority_identifier {$reg-auth},
            attribute data_identifier {$data-identifier},
            attribute version {$version},
            $content
           }
      ) else (
       element openMDR:Non_Enumerated_Value_Domain {
            attribute item_registration_authority_identifier {$reg-auth},
            attribute data_identifier {$data-identifier},
            attribute version {$version},
            $content
           }
      )
   )

   let $collection := 'value_domain'
   let $message := lib-forms:store-document($document)
   return
      if ($message='stored')
      then true()
      else response:redirect-to(xs:anyURI(concat("../web/login.xquery?calling_page=newValueDomain.xquery&",$message)))
};

declare function local:input-page(
   $message as xs:string?,
   $reg-auth as xs:string?,
   $administrative-note  as xs:string?,
   $administrative-status  as xs:string?,
   $administered-by  as xs:string?,
   $submitted-by  as xs:string?,
   $registered-by  as xs:string?,
   $context-ids  as xs:string*,
   $country-identifiers as xs:string*,
   $language-identifiers as xs:string*,
   $names as xs:string*,
   $definitions as xs:string*,
   $sources as xs:string*,
   $action as xs:string?,
   $preferred as xs:string?,
   $conceptual_domain_id as xs:string?,
   $enum_datatype as xs:string?,
   $enum_uom as xs:string?,
   $values as xs:string*
   ) {
   let $skip-name := substring-after($action,'delete naming entry')
   let $skip-name-index := if ($skip-name>'') then xs:int($skip-name) else 0

   return

                This form will allow you to create a new value domain in the metadata repository

          <form name="new_value_domain" action="newValueDomain.xquery" method="post" class="cagridForm" enctype="multipart/form-data">

           {lib-forms:edit-admin-item($reg-auth,
                     $administrative-note,
                     $administrative-status,
                     $administered-by,
                     $submitted-by,
                     $registered-by,
                     $context-ids,
                     $country-identifiers,
                     $language-identifiers,
                     $names,
                     $definitions,
                     $sources,
                     $preferred,
                     $action)}

Conceptual Domain

                        {
                            let $concept_domain := lib-util:mdrElement("conceptual_domain",$conceptual_domain_id)
                            return

                            if ($conceptual_domain_id > '') then (

                                    Conceptual Domain ID
                                    {$conceptual_domain_id}
                                    {lib-forms:hidden-element('conceptual_domain_id',$conceptual_domain_id)}

,

                                    Conceptual Domain Name
                                    {administered-item:preferred-name('conceptual_domain',$conceptual_domain_id)}

,

Value Domain
,

                                   Value Domain Data Type
                                   {lib-forms:make-select-datatype('enum_datatype', request:get-parameter('enum_datatype',''))}

,

                                   Value Domain Unit of Measure
                                   {lib-forms:make-select-uom('enum_uom',request:get-parameter('uom',''))}

,
                               if($concept_domain//openMDR:value_meaning_description > '')
                               then
                               (

                                        Possible Values	meaning	value

,
                                        for $meaning at $pos in $concept_domain//openMDR:value_meaning_description
                                        return (

                                              Permissable Value {$pos}
                                              {$meaning}
                                              {lib-forms:input-element('values', 20, $values[$pos])}

                                        )
                               ) else ()
                            )
                            else (

                                    Choose Conceptual Domain
                                    {lib-forms:make-select-admin-item('conceptual_domain','conceptual_domain_id',$conceptual_domain_id)}
                                    {lib-forms:action-button('select', 'action','')}

                            )
                        }

                                Store

                                <input type="submit" name="update" value="Store"/>
                                <input type="submit" name="update" value="Clear"/>

          </form>

{$message}

   };

declare function local:success-page()
{
   let $calling-page := request:get-parameter("calling-page","")
   return

Value Domain class created

Return to maintenance menu

Create another value domain

};

declare option exist:serialize "media-type=text/html method=xhtml doctype-public=-//W3C//DTD XHTML 1.0 Transitional//EN doctype-system=http://www.w3.org/TR/2002/REC-xhtml1-20020801/DTD/xhtml1-transitional.dtd";

   session:create(),
   let $title as xs:string := "Creating a New Value Domain"
   let $reg-auth := request:get-parameter('registration-authority','')
   let $administrative-note := request:get-parameter('administrative-note','')
   let $administrative-status := request:get-parameter('administrative-status','')
   let $administered-by := request:get-parameter('administered-by','')
   let $submitted-by := request:get-parameter('submitted-by','')

   let $registered-by := request:get-parameter('registered-by','')
   let $context-ids := request:get-parameter('context-ids',())
   let $country-identifiers := request:get-parameter('country-identifiers',())
   let $language-identifiers := request:get-parameter('language-identifiers',())
   let $names := request:get-parameter('names',())
   let $definitions := request:get-parameter('definitions',())
   let $sources := request:get-parameter('sources',())
   let $preferred := request:get-parameter('preferred','')
   let $action := request:get-parameter('update','')
   let $conceptual_domain_id as xs:string? := request:get-parameter('conceptual_domain_id','')
   let $values := request:get-parameter('values',())
   let $enum_datatype := request:get-parameter('enum_datatype','')
   let $enum_uom := request:get-parameter('enum_uom','')
   (:
   let $log := util:log-system-err($values)
    :)

   return
      lib-rendering:txfrm-webpage(
      $title,
      if ($action='Store')
      then
         (
         if (
               local:value_domain
                  (
                     $reg-auth,
                     $administrative-note,
                     $administrative-status,
                     $administered-by,
                     $submitted-by,
                     $registered-by,
                     $context-ids,
                     $country-identifiers,
                     $language-identifiers,
                     $names,
                     $definitions,
                     $sources,
                     $preferred,
                     $conceptual_domain_id,
                     $enum_datatype,
                     $enum_uom,
                     $values
                  )
            )
         then local:success-page()
         else (local:input-page(
            'could not store document',
                     $reg-auth,
                     $administrative-note,
                     $administrative-status,
                     $administered-by,
                     $submitted-by,
                     $registered-by,
                     $context-ids,
                     $country-identifiers,
                     $language-identifiers,
                     $names,
                     $definitions,
                     $sources,
                     $action,
                     $preferred,
                     $conceptual_domain_id,
                     $enum_datatype,
                     $enum_uom,
                     $values
                  )
               )
         )
      else local:input-page
               (
               '',
               $reg-auth,
               $administrative-note,
               $administrative-status,
               $administered-by,
               $submitted-by,
               $registered-by,
               $context-ids,
               $country-identifiers,
               $language-identifiers,
               $names,
               $definitions,
               $sources,
               $action,
               $preferred,
               $conceptual_domain_id,
               $enum_datatype,
               $enum_uom,
               $values
               )
         )

xquery version "1.0";

(: ~
 : Module Name:             new value domain webpage and XQuery
 :
 : Module overview          Creates and value domain and displays list
 :)

(:~
 :    @author Rakesh Dhaval
 :    @version 0.1
~ :)

  import module namespace
  lib-forms="http://www.cagrid.org/xquery/library/forms"
  at "../edit/m-lib-forms.xquery";

  import module namespace
  lib-util="http://www.cagrid.org/xquery/library/util"
  at "../library/m-lib-util.xquery";

  import module namespace
  lib-rendering="http://www.cagrid.org/xquery/library/rendering"
  at "../web/m-lib-rendering.xquery";

  import module namespace
    lib-make-admin-item="http://www.cagrid.org/xquery/library/make-admin-item"
    at "../edit/m-lib-make-admin-item.xquery";

  import module namespace
   administered-item="http://www.cagrid.org/xquery/library/administered-item"
   at "../library/m-administered-item.xquery";

declare namespace openMDR = "http://www.cagrid.org/schema/openMDR";
declare namespace ISO11179= "http://www.cagrid.org/schema/ISO11179";
declare namespace session="http://exist-db.org/xquery/session";
declare namespace response="http://exist-db.org/xquery/response";
declare namespace exist = "http://exist.sourceforge.net/NS/exist";

declare function local:value_domain(
   $reg-auth as xs:string,
   $administrative-note as xs:string,
   $administrative-status as xs:string,
   $administered-by as xs:string,
   $submitted-by as xs:string,
   $registered-by as xs:string,
   $context-ids as xs:string*,
   $country-identifiers as xs:string*,
   $language-identifiers as xs:string*,
   $names as xs:string*,
   $definitions as xs:string*,
   $sources as xs:string*,
   $preferred as xs:string?,
   $conceptual_domain_id as xs:string?,
   $enum_datatype as xs:string?,
   $enum_uom as xs:string?,
   $values as xs:string*
   ) as xs:boolean
{
   let $version := '0.1'
   let $data-identifier := lib-forms:generate-id()
   let $new-identifier := concat($reg-auth, '-', $data-identifier, '-', $version)
   let $doc-name := concat($new-identifier,'.xml')
   let $concept_domain := lib-util:mdrElement("conceptual_domain",$conceptual_domain_id)

   let $content := (
            lib-make-admin-item:administration-record($administrative-note,$administrative-status,'Recorded'),
            lib-make-admin-item:custodians($administered-by,$registered-by,$submitted-by),
            lib-make-admin-item:havings(
                    $context-ids,
                    $country-identifiers,
                    $language-identifiers,
                    $names,
                    $definitions,
                    $preferred,
                    $sources),

             for $meaning at $pos in $concept_domain//openMDR:value_meaning_description
                    return (
                       element openMDR:containing {
                         attribute permissible_value_identifier {lib-forms:generate-id()},
                         element openMDR:permissible_value_begin_date {current-date()},
                         element openMDR:value_item {$values[$pos]},
                         element openMDR:contained_in {$concept_domain//openMDR:value_meaning_identifier[$pos]/text()}
                       }
             ),
            element openMDR:representing {$conceptual_domain_id},
            element openMDR:value_domain_datatype {$enum_datatype},
            element openMDR:value_domain_unit_of_measure {$enum_uom}

)

   (: compose the document :)
   let $document := (
     if($values > '' ) then (
      element openMDR:Enumerated_Value_Domain {
            attribute item_registration_authority_identifier {$reg-auth},
            attribute data_identifier {$data-identifier},
            attribute version {$version},
            $content
           }
      ) else (
       element openMDR:Non_Enumerated_Value_Domain {
            attribute item_registration_authority_identifier {$reg-auth},
            attribute data_identifier {$data-identifier},
            attribute version {$version},
            $content
           }
      )
   )

   let $collection := 'value_domain'
   let $message := lib-forms:store-document($document)
   return
      if ($message='stored')
      then true()
      else response:redirect-to(xs:anyURI(concat("../web/login.xquery?calling_page=newValueDomain.xquery&",$message)))
};

declare function local:input-page(
   $message as xs:string?,
   $reg-auth as xs:string?,
   $administrative-note  as xs:string?,
   $administrative-status  as xs:string?,
   $administered-by  as xs:string?,
   $submitted-by  as xs:string?,
   $registered-by  as xs:string?,
   $context-ids  as xs:string*,
   $country-identifiers as xs:string*,
   $language-identifiers as xs:string*,
   $names as xs:string*,
   $definitions as xs:string*,
   $sources as xs:string*,
   $action as xs:string?,
   $preferred as xs:string?,
   $conceptual_domain_id as xs:string?,
   $enum_datatype as xs:string?,
   $enum_uom as xs:string?,
   $values as xs:string*
   ) {
   let $skip-name := substring-after($action,'delete naming entry')
   let $skip-name-index := if ($skip-name>'') then xs:int($skip-name) else 0

   return

                This form will allow you to create a new value domain in the metadata repository

          <form name="new_value_domain" action="newValueDomain.xquery" method="post" class="cagridForm" enctype="multipart/form-data">

           {lib-forms:edit-admin-item($reg-auth,
                     $administrative-note,
                     $administrative-status,
                     $administered-by,
                     $submitted-by,
                     $registered-by,
                     $context-ids,
                     $country-identifiers,
                     $language-identifiers,
                     $names,
                     $definitions,
                     $sources,
                     $preferred,
                     $action)}

Conceptual Domain

                        {
                            let $concept_domain := lib-util:mdrElement("conceptual_domain",$conceptual_domain_id)
                            return

                            if ($conceptual_domain_id > '') then (

                                    Conceptual Domain ID
                                    {$conceptual_domain_id}
                                    {lib-forms:hidden-element('conceptual_domain_id',$conceptual_domain_id)}

,

                                    Conceptual Domain Name
                                    {administered-item:preferred-name('conceptual_domain',$conceptual_domain_id)}

,

Value Domain
,

                                   Value Domain Data Type
                                   {lib-forms:make-select-datatype('enum_datatype', request:get-parameter('enum_datatype',''))}

,

                                   Value Domain Unit of Measure
                                   {lib-forms:make-select-uom('enum_uom',request:get-parameter('uom',''))}

,
                               if($concept_domain//openMDR:value_meaning_description > '')
                               then
                               (

                                        Possible Values	meaning	value

,
                                        for $meaning at $pos in $concept_domain//openMDR:value_meaning_description
                                        return (

                                              Permissable Value {$pos}
                                              {$meaning}	{lib-forms:input-element('values', 20, $values[$pos])}

                                        )
                               ) else ()
                            )
                            else (

                                    Choose Conceptual Domain
                                    {lib-forms:make-select-admin-item('conceptual_domain','conceptual_domain_id',$conceptual_domain_id)}
                                    {lib-forms:action-button('select', 'action','')}

                            )
                        }

                                Store

                                <input type="submit" name="update" value="Store"/>
                                <input type="submit" name="update" value="Clear"/>

          </form>

{$message}

   };

declare function local:success-page()
{
   let $calling-page := request:get-parameter("calling-page","")
   return

Value Domain class created

Return to maintenance menu

Create another value domain

};

declare option exist:serialize "media-type=text/html method=xhtml doctype-public=-//W3C//DTD XHTML 1.0 Transitional//EN doctype-system=http://www.w3.org/TR/2002/REC-xhtml1-20020801/DTD/xhtml1-transitional.dtd";

   session:create(),
   let $title as xs:string := "Creating a New Value Domain"
   let $reg-auth := request:get-parameter('registration-authority','')
   let $administrative-note := request:get-parameter('administrative-note','')
   let $administrative-status := request:get-parameter('administrative-status','')
   let $administered-by := request:get-parameter('administered-by','')
   let $submitted-by := request:get-parameter('submitted-by','')

   let $registered-by := request:get-parameter('registered-by','')
   let $context-ids := request:get-parameter('context-ids',())
   let $country-identifiers := request:get-parameter('country-identifiers',())
   let $language-identifiers := request:get-parameter('language-identifiers',())
   let $names := request:get-parameter('names',())
   let $definitions := request:get-parameter('definitions',())
   let $sources := request:get-parameter('sources',())
   let $preferred := request:get-parameter('preferred','')
   let $action := request:get-parameter('update','')
   let $conceptual_domain_id as xs:string? := request:get-parameter('conceptual_domain_id','')
   let $values := request:get-parameter('values',())
   let $enum_datatype := request:get-parameter('enum_datatype','')
   let $enum_uom := request:get-parameter('enum_uom','')
   (:
   let $log := util:log-system-err($values)
   let $log := util:log-system-err($enum_datatype)
   let $log := util:log-system-err($enum_uom)
    :)

   return
      lib-rendering:txfrm-webpage(
      $title,
      if ($action='Store')
      then
         (
         if (
               local:value_domain
                  (
                     $reg-auth,
                     $administrative-note,
                     $administrative-status,
                     $administered-by,
                     $submitted-by,
                     $registered-by,
                     $context-ids,
                     $country-identifiers,
                     $language-identifiers,
                     $names,
                     $definitions,
                     $sources,
                     $preferred,
                     $conceptual_domain_id,
                     $enum_datatype,
                     $enum_uom,
                     $values
                  )
            )
         then local:success-page()
         else (local:input-page(
            'could not store document',
                     $reg-auth,
                     $administrative-note,
                     $administrative-status,
                     $administered-by,
                     $submitted-by,
                     $registered-by,
                     $context-ids,
                     $country-identifiers,
                     $language-identifiers,
                     $names,
                     $definitions,
                     $sources,
                     $action,
                     $preferred,
                     $conceptual_domain_id,
                     $enum_datatype,
                     $enum_uom,
                     $values
                  )
               )
         )
      else local:input-page
               (
               '',
               $reg-auth,
               $administrative-note,
               $administrative-status,
               $administered-by,
               $submitted-by,
               $registered-by,
               $context-ids,
               $country-identifiers,
               $language-identifiers,
               $names,
               $definitions,
               $sources,
               $action,
               $preferred,
               $conceptual_domain_id,
               $enum_datatype,
               $enum_uom,
               $values
               )
         )


Removed old code - now uses security module

svn path=/trunk/eXist/; revision=12763

xquery version "1.0";

(:~
    The core XQuery script for the bibliographic demo. It receives a template XML document
    from the controller and expands it. If a search was trigger by the user, the script
    proceeds as follows:

the input form parameters are transformed into a simple XML structure
            to describe the query

an XPath string is generated from the XML query structure

the XPath is executed and the sort criteria applied

query results, XML query and sort criteria are stored into the HTTP session

the template is expanded, forms are regenerated to match the query

    To apply a filter to an existing query, we just extend the XML representation
    of the query.
:)
import module namespace jquery="http://exist-db.org/xquery/jquery" at "resource:org/exist/xquery/lib/jquery.xql";

declare namespace biblio="http:/exist-db.org/xquery/biblio";

declare namespace request="http://exist-db.org/xquery/request";
declare namespace session="http://exist-db.org/xquery/session";
declare namespace util="http://exist-db.org/xquery/util";
declare namespace xmldb="http://exist-db.org/xquery/xmldb";

import module namespace config="http://exist-db.org/mods/config" at "config.xqm";
import module namespace mods="http://www.loc.gov/mods/v3" at "retrieve-mods.xql";
import module namespace sort="http://exist-db.org/xquery/sort" at "java:org.exist.xquery.modules.sort.SortModule";
import module namespace security="http://exist-db.org/mods/security" at "security.xqm";

declare option exist:serialize "method=xhtml media-type=application/xhtml+xml omit-xml-declaration=no enforce-xhtml=yes";

(:~
    Simple mapping from field names to an XPath expression
:)
declare variable $biblio:FIELDS :=
	<fields>
		<field name="Title">(
		mods:mods[ft:query(mods:titleInfo, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:titleInfo, '$q', $options)]
		)</field>
		<field name="Name">(
		mods:mods[ft:query(mods:name, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:name, '$q', $options)]
		)</field>
		<field name="Date">(
		mods:mods[ft:query(mods:originInfo/mods:dateCreated, '$q', $options)]
		      union
		mods:mods[ft:query(mods:originInfo/mods:dateIssued, '$q', $options)]
		      union
		mods:mods[ft:query(mods:originInfo/mods:dateCaptured, '$q', $options)]
		      union
		mods:mods[ft:query(mods:originInfo/mods:copyrightDate, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:originInfo/mods:dateCreated, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:originInfo/mods:dateIssued, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:originInfo/mods:dateCaptured, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:originInfo/mods:copyrightDate, '$q', $options)]
		)</field>
		<field name="Abstract">mods:mods[ft:query(mods:abstract, '$q', $options)]</field>
        <field name="Note">mods:mods[ft:query(mods:note, '$q', $options)]</field>
        <field name="Subject">mods:mods[ft:query(mods:subject, '$q', $options)]</field>
        <field name="All Except Date">(
        mods:mods[ft:query(.//*, '$q', $options)]
		)</field>

	</fields>;

(:
    Default template to be used for form generation if no
    query was specified
:)
declare variable $biblio:TEMPLATE_QUERY :=
    <query>
        <collection>{$config:mods-root}</collection>
        <and>
            <field m="1" name="All"></field>
        </and>
    </query>;

(:~
    Regenerate the HTML form to match the query, e.g. after adding more filter
    clauses.
:)
declare function biblio:form-from-query($query as element()) as element()+ {
    for $field at $pos in $query//field
    return

            {
                let $operator :=
                    if ($field/preceding-sibling::*) then
                        $field/../local-name(.)
                    else
                        ()
                return
                    <select name="operator{$pos}">
                    { if (empty($operator)) then attribute style { "display: none;" } else () }
                    {
                        for $opt in ("and", "or", "not")
                        return
                            <option>
                            {
                                if ($opt eq $operator) then
                                    attribute selected { "selected" }
                                else
                                    ()
                            }
                            { $opt }
                            </option>
                    }
                    </select>
            }

                <select name="field{$pos}">
                {
                    for $f in $biblio:FIELDS/field
                    return
                        <option>
                            { if ($f/@name eq $field/@name) then attribute selected { "selected" } else () }
                            {$f/@name/string()}
                        </option>
                }
                </select>

                <jquery:input name="input{$pos}" value="{$field/string()}">
                    <jquery:autocomplete url="autocomplete.xql"
                        width="300" multiple="false"
                        matchContains="false"
                        paramsCallback="autocompleteCallback">
                    </jquery:autocomplete>
                </jquery:input>

};

(:~
    Generate an XPath query string from the given XML representation
    of the query.
:)
declare function biblio:generate-query($xml as element()) as xs:string* {
    typeswitch ($xml)
        case element(query) return
            for $child in $xml/*
            return
                biblio:generate-query($child)
        case element(and) return
            (
                biblio:generate-query($xml/*[1]),
                " intersect ",
                biblio:generate-query($xml/*[2])
            )
        case element(or) return
            (
                biblio:generate-query($xml/*[1]),
                " union ",
                biblio:generate-query($xml/*[2])
            )
        case element(not) return
            (
                biblio:generate-query($xml/*[1]),
                " except ",
                biblio:generate-query($xml/*[2])
            )
        case element(field) return
            let $expr0 := $biblio:FIELDS/field[@name = $xml/@name]
            let $expr := if ($expr0) then $expr0 else $biblio:FIELDS/field[last()]
            let $collection := concat("collection('", $xml/ancestor::query/collection/string(), "')//")
            return
                ($collection, replace($expr, '\$q', $xml/string()))
        case element(collection) return
            if (not($xml/..//field)) then
                ('collection("', $xml/string(), '")//mods:mods')
            else
                ()
        default return
            ()
};

(:~
    Transform the XML representation of the query into a simple string
    for display to the user in the query history.
:)
declare function biblio:xml-query-to-string($xml as element()) as xs:string* {
    typeswitch ($xml)
        case element(query) return
            biblio:xml-query-to-string($xml/*[1])
        case element(and) return
            (
                biblio:xml-query-to-string($xml/*[1]),
                " AND ",
                biblio:xml-query-to-string($xml/*[2])
            )
        case element(or) return
            (
                biblio:xml-query-to-string($xml/*[1]),
                " OR ",
                biblio:xml-query-to-string($xml/*[2])
            )
        case element(not) return
            (
                biblio:xml-query-to-string($xml/*[1]),
                " NOT ",
                biblio:xml-query-to-string($xml/*[2])
            )
        case element(field) return
            concat($xml/@name, ':', $xml/string())
        default return
            ()
};

(:~
    Process single form parameter. Called from biblio:process-form().
:)
declare function biblio:process-form-parameters($params as xs:string*) as element() {
    let $param := $params[1]
    let $n := substring-after($param, 'input')
    let $value := request:get-parameter($param, "")
    let $field := request:get-parameter(concat("field", $n), 'all')
    let $operator := request:get-parameter(concat("operator", $n), "and")
    return
        if (count($params) eq 1) then
            <field m="{$n}" name="{$field}">{$value}</field>
        else
            element { xs:QName($operator) } {
                biblio:process-form-parameters(subsequence($params, 2)),
                <field m="{$n}" name="{$field}">{$value}</field>
            }
};

(:~
    Process the received form parameters and create an XML representation of
    the query. Filter out empty parameters and take care of boolean operators.
:)
declare function biblio:process-form() as element(query)? {
    let $collection := request:get-parameter("collection", $config:mods-root)
    let $fields :=
        (:  Get a list of all input parameters which are not empty,
            ordered by input name. :)
        for $param in request:get-parameter-names()[starts-with(., 'input')]
        let $value := request:get-parameter($param, ())
        where string-length($value) gt 0
        order by $param descending
        return
            $param
    return
        if (exists($fields)) then
            (:  process-form recursively calls itself for every parameter and
                generates and XML representation of the query. :)
            <query>
                <collection>{$collection}</collection>
                { biblio:process-form-parameters($fields) }
            </query>
        else
            <query>
                <collection>{$collection}</collection>
            </query>
};

(:~
    Helper function used to sort by name within the "order by"
    clause of the query.
:)
declare function biblio:orderByName($m as element()) as xs:string?
{
    for $name in $m/mods:name[1]
    return
        mods:retrieve-name($name, 1)
};

(: Map order parameter to xpath for order by clause :)
declare function biblio:orderExpr($field as xs:string?) as xs:string
{
    if (sort:has-index('mods:name')) then
        if ($field eq "Score") then
            "ft:score($hit) descending"
        else if ($field = "Author") then
            "sort:index('mods:name', $hit)"
        else if ($field = "Title") then
            "sort:index('mods:title', $hit)"
        else
            "sort:index('mods:date', $hit)"
    else
        if ($field eq "Score") then
            "ft:score($hit) descending"
        else if ($field = "Author") then
            "biblio:orderByName($hit)"
        else if ($field = "Title") then
            "$hit/mods:titleInfo[1]/mods:title[1]"
        else
            "$hit/mods:originInfo/mods:dateCreated[1] descending"
};

(:~
    Evaluate the actual XPath query and order the results
:)
declare function biblio:evaluate-query($query as xs:string, $sort as xs:string?) {
    let $sortExpr := biblio:orderExpr($sort)
    let $orderedQuery :=
            concat("for $hit in ", $query, " order by ", $sortExpr, " return $hit")
    let $options :=
        <options>
            <default-operator>and</default-operator>
        </options>
    return
        util:eval($orderedQuery)
};

(:~
    Add a query to the user's query history. We store the XML representation
    of the query.
:)
declare function biblio:add-to-history($queryAsXML as element()) {
    let $oldHistory := session:get-attribute('history')
    let $newHistory :=
        let $n := if ($oldHistory) then max(for $n in $oldHistory/query/@n return xs:int($n)) + 1 else 1
        return
            <history>
                <query id="q{$n}" n="{$n}">
                    { $queryAsXML/* }
                </query>
                { $oldHistory/query }
            </history>
    return
        session:set-attribute('history', $newHistory)
};

(:~
    Retrieve a query from the query history
:)
declare function biblio:query-from-history($id as xs:string) {
    let $history := session:get-attribute('history')
    return
        $history/query[@id = $id]
};

(:~
    Returns the query history as a HTML list. The queries are
    transformed into a simple string representation.
:)
declare function biblio:query-history() {

    {
        let $history := session:get-attribute('history')
        for $query at $pos in $history/query
        return

{biblio:xml-query-to-string($query)}

    }

};

(:~
    Evaluate the query given as XML and store its results into the HTTP session
    for later reference.
:)
declare function biblio:eval-query($queryAsXML as element()?) {
    if ($queryAsXML) then
        let $query := string-join(biblio:generate-query($queryAsXML), '')
        let $log := util:log("DEBUG", ("QUERY: ", $query))
        let $sort0 := request:get-parameter("sort", ())
        let $sort := if ($sort0) then $sort0 else session:get-attribute("sort")
        let $results := biblio:evaluate-query($query, $sort)
        (:~ Take the query results and store them into the HTTP session. :)
        let $null := session:set-attribute('mods:cached', $results)
        let $null := session:set-attribute('query', $queryAsXML)
        let $null := session:set-attribute('sort', $queryAsXML)
        let $null := biblio:add-to-history($queryAsXML)
        return
            count($results)
    else
        0
};

(:~
    Clear the last query result.
:)
declare function biblio:clear() {
    let $null := session:remove-attribute('mods:cached')
    let $null := session:remove-attribute('query')
    let $null := session:remove-attribute('sort')
    return
        ()
};

(:~
    Scan the input HTML template and expand the biblio:* tags
    found therein.
:)
declare function biblio:process-templates($query as element()?, $hitCount as xs:integer?, $node as node()) {
    typeswitch ($node)
        case element(biblio:login) return
            let $user := request:get-attribute("xquery.user")
            return (
                if ($user eq 'guest') then

Login

                else

Logged in as {$user}. Logout

            )
        case element(biblio:form-from-query) return
            biblio:form-from-query($query)
        case element(biblio:result-count) return
            text { $hitCount }
        case element(biblio:query-history) return
            biblio:query-history()
        case element(biblio:collection-path) return
            let $collection := request:get-parameter("collection", $config:mods-root)
            return
                <input class="collection-input" type="text" name="collection" value="{$collection}" readonly="true"/>
        case element(biblio:form-select-current-user-groups) return
            biblio:form-select-current-user-groups($node/@name)
        case element(biblio:current-user) return
            {request:get-attribute("xquery.user")}
        case element(biblio:conditional) return
            let $result := biblio:conditional($node) return
                if($result)then
                (
                    for $child in $result/node() return
                        biblio:process-templates($query, $hitCount, $child)
                )
                else()
        case element(biblio:is-collection-owner) return
            security:is-collection-owner(security:get-user-credential-from-session()[1], request:get-parameter("collection", $config:mods-root))
        case element(biblio:has-collection-write-permissions) return
            (   util:log("debug", concat("LOOK HERE: user=", security:get-user-credential-from-session()[1], " collection=", request:get-parameter("collection", $config:mods-root))),
                security:can-write-collection(security:get-user-credential-from-session()[1], request:get-parameter("collection", $config:mods-root))
            )
        case element(biblio:form-select-collection) return
            biblio:form-select-collection($node/@name)
        case element() return
            element { node-name($node) } {
                $node/@*,
                for $child in $node/node() return
                    biblio:process-templates($query, $hitCount, $child)
            }
        default return
            $node
};

declare function biblio:form-select-current-user-groups($select-name as xs:string) as element(select) {
    let $user := request:get-attribute("xquery.user") return
        <select name="{$select-name}">
        {
            for $group in xmldb:get-user-groups($user) return
                <option value="{$group}">{$group}</option>
        }
        </select>
};

declare function biblio:form-select-collection($select-name as xs:string) as element(select) {

    let $current-collection := request:get-parameter("collection", $config:mods-root) return

        <select name="{$select-name}">
        {
            if(security:can-write-collection(security:get-user-credential-from-session()[1], "/db"))then
            (
                element option {
                    if("/db" eq $current-collection)then
                    (
                        attribute selected { "selected" }
                    )else(),
                    text { "/db" }
                }
            )else(),

            for $sub-collection-path in biblio:get-writeable-subcollection-paths("/db") return
                element option {
                    if($sub-collection-path eq $current-collection)then
                    (
                        attribute selected { "selected" }
                    )else(),
                    text { $sub-collection-path }
                }
        }
        </select>
};

declare function biblio:get-writeable-subcollection-paths($path as xs:string) {

	for $sub in xmldb:get-child-collections($path)
	let $col := concat($path, "/", $sub) return
		(
			if(security:can-write-collection(security:get-user-credential-from-session()[1], $col))then
			(
			 $col
			)else(),
			biblio:get-writeable-subcollection-paths($col)
		)
};

declare function biblio:conditional($node as element(biblio:conditional)) {
    let $test-result := biblio:process-templates((), (), $node/biblio:test/biblio:*) return
        if($test-result) then
        (
            $node/biblio:result
        )else()
};

(:~
    Filter an existing result set by applying an additional
    clause with "and".
:)
declare function biblio:apply-filter() {
    let $prevQuery := session:get-attribute("query")
    let $filter := request:get-parameter("filter", ())
    let $value := request:get-parameter("value", ())
    return
        if ($filter = ('All', 'Title') and count($prevQuery/field) eq 1) then
            <query>
                <field>{$prevQuery/field/@name,
                    normalize-space(concat($prevQuery/field/string(), ' ', $value))
                }</field>
            </query>
        else
            <query>
                <and>
                { $prevQuery/* }
                { <field name="{$filter}">{$value}</field> }
                </and>
            </query>
};

session:create(),
(: We receive an HTML template as input :)
let $input := request:get-data()
let $filter := request:get-parameter("filter", ())
let $history := request:get-parameter("history", ())
let $clear := request:get-parameter("clear", ())
let $mylist := request:get-parameter("mylist", ())
let $collection := request:get-parameter("collection", ())

(: Process request parameters and generate an XML representation of the query :)
let $queryAsXML :=
    if ($history) then
        biblio:query-from-history($history)
    else if ($clear) then
        biblio:clear()
    else if ($filter) then
        biblio:apply-filter()
    else if ($mylist eq 'display') then
        ()
    else
        biblio:process-form()
let $log := util:log("DEBUG", ("$queryAsXML: ", $queryAsXML))
(: Evaluate the query :)
let $results :=
    if ($mylist) then (
        if ($mylist eq 'clear') then
            session:set-attribute("personal-list", ())
        else
            (),
        let $list := session:get-attribute("personal-list")
        let $items :=
            for $item in $list/listitem
            return
                util:node-by-id(doc(substring-before($item/@id, '#')), substring-after($item/@id, '#'))
        let $null := session:set-attribute('mods:cached', $items)
        return
            count($items)
    ) else
        biblio:eval-query($queryAsXML)
(:  Process the HTML template received as input :)
let $output :=
    jquery:process(
        biblio:process-templates(if ($queryAsXML//field) then $queryAsXML else $biblio:TEMPLATE_QUERY, $results, $input)
    )
return
    $output

xquery version "1.0";

(:~
    The core XQuery script for the bibliographic demo. It receives a template XML document
    from the controller and expands it. If a search was trigger by the user, the script
    proceeds as follows:

the input form parameters are transformed into a simple XML structure
            to describe the query

an XPath string is generated from the XML query structure

the XPath is executed and the sort criteria applied

query results, XML query and sort criteria are stored into the HTTP session

the template is expanded, forms are regenerated to match the query

    To apply a filter to an existing query, we just extend the XML representation
    of the query.
:)
import module namespace jquery="http://exist-db.org/xquery/jquery" at "resource:org/exist/xquery/lib/jquery.xql";

declare namespace biblio="http:/exist-db.org/xquery/biblio";

declare namespace request="http://exist-db.org/xquery/request";
declare namespace session="http://exist-db.org/xquery/session";
declare namespace util="http://exist-db.org/xquery/util";
declare namespace xmldb="http://exist-db.org/xquery/xmldb";

import module namespace config="http://exist-db.org/mods/config" at "config.xqm";
import module namespace mods="http://www.loc.gov/mods/v3" at "retrieve-mods.xql";
import module namespace sort="http://exist-db.org/xquery/sort" at "java:org.exist.xquery.modules.sort.SortModule";
import module namespace security="http://exist-db.org/mods/security" at "security.xqm";

declare option exist:serialize "method=xhtml media-type=application/xhtml+xml omit-xml-declaration=no enforce-xhtml=yes";

(:~
    Simple mapping from field names to an XPath expression
:)
declare variable $biblio:FIELDS :=
	<fields>
		<field name="Title">(
		mods:mods[ft:query(mods:titleInfo, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:titleInfo, '$q', $options)]
		)</field>
		<field name="Name">(
		mods:mods[ft:query(mods:name, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:name, '$q', $options)]
		)</field>
		<field name="Date">(
		mods:mods[ft:query(mods:originInfo/mods:dateCreated, '$q', $options)]
		      union
		mods:mods[ft:query(mods:originInfo/mods:dateIssued, '$q', $options)]
		      union
		mods:mods[ft:query(mods:originInfo/mods:dateCaptured, '$q', $options)]
		      union
		mods:mods[ft:query(mods:originInfo/mods:copyrightDate, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:originInfo/mods:dateCreated, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:originInfo/mods:dateIssued, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:originInfo/mods:dateCaptured, '$q', $options)]
		      union
		mods:mods[ft:query(mods:relatedItem/mods:originInfo/mods:copyrightDate, '$q', $options)]
		)</field>
		<field name="Abstract">mods:mods[ft:query(mods:abstract, '$q', $options)]</field>
        <field name="Note">mods:mods[ft:query(mods:note, '$q', $options)]</field>
        <field name="Subject">mods:mods[ft:query(mods:subject, '$q', $options)]</field>
        <field name="All Except Date">(
        mods:mods[ft:query(.//*, '$q', $options)]
		)</field>

	</fields>;

(:
    Default template to be used for form generation if no
    query was specified
:)
declare variable $biblio:TEMPLATE_QUERY :=
    <query>
        <collection>{$config:mods-root}</collection>
        <and>
            <field m="1" name="All"></field>
        </and>
    </query>;

(:~
    Regenerate the HTML form to match the query, e.g. after adding more filter
    clauses.
:)
declare function biblio:form-from-query($query as element()) as element()+ {
    for $field at $pos in $query//field
    return

            {
                let $operator :=
                    if ($field/preceding-sibling::*) then
                        $field/../local-name(.)
                    else
                        ()
                return
                    <select name="operator{$pos}">
                    { if (empty($operator)) then attribute style { "display: none;" } else () }
                    {
                        for $opt in ("and", "or", "not")
                        return
                            <option>
                            {
                                if ($opt eq $operator) then
                                    attribute selected { "selected" }
                                else
                                    ()
                            }
                            { $opt }
                            </option>
                    }
                    </select>
            }

                <select name="field{$pos}">
                {
                    for $f in $biblio:FIELDS/field
                    return
                        <option>
                            { if ($f/@name eq $field/@name) then attribute selected { "selected" } else () }
                            {$f/@name/string()}
                        </option>
                }
                </select>

                <jquery:input name="input{$pos}" value="{$field/string()}">
                    <jquery:autocomplete url="autocomplete.xql"
                        width="300" multiple="false"
                        matchContains="false"
                        paramsCallback="autocompleteCallback">
                    </jquery:autocomplete>
                </jquery:input>

};

(:~
    Generate an XPath query string from the given XML representation
    of the query.
:)
declare function biblio:generate-query($xml as element()) as xs:string* {
    typeswitch ($xml)
        case element(query) return
            for $child in $xml/*
            return
                biblio:generate-query($child)
        case element(and) return
            (
                biblio:generate-query($xml/*[1]),
                " intersect ",
                biblio:generate-query($xml/*[2])
            )
        case element(or) return
            (
                biblio:generate-query($xml/*[1]),
                " union ",
                biblio:generate-query($xml/*[2])
            )
        case element(not) return
            (
                biblio:generate-query($xml/*[1]),
                " except ",
                biblio:generate-query($xml/*[2])
            )
        case element(field) return
            let $expr0 := $biblio:FIELDS/field[@name = $xml/@name]
            let $expr := if ($expr0) then $expr0 else $biblio:FIELDS/field[last()]
            let $collection := concat("collection('", $xml/ancestor::query/collection/string(), "')//")
            return
                ($collection, replace($expr, '\$q', $xml/string()))
        case element(collection) return
            if (not($xml/..//field)) then
                ('collection("', $xml/string(), '")//mods:mods')
            else
                ()
        default return
            ()
};

(:~
    Transform the XML representation of the query into a simple string
    for display to the user in the query history.
:)
declare function biblio:xml-query-to-string($xml as element()) as xs:string* {
    typeswitch ($xml)
        case element(query) return
            biblio:xml-query-to-string($xml/*[1])
        case element(and) return
            (
                biblio:xml-query-to-string($xml/*[1]),
                " AND ",
                biblio:xml-query-to-string($xml/*[2])
            )
        case element(or) return
            (
                biblio:xml-query-to-string($xml/*[1]),
                " OR ",
                biblio:xml-query-to-string($xml/*[2])
            )
        case element(not) return
            (
                biblio:xml-query-to-string($xml/*[1]),
                " NOT ",
                biblio:xml-query-to-string($xml/*[2])
            )
        case element(field) return
            concat($xml/@name, ':', $xml/string())
        default return
            ()
};

(:~
    Process single form parameter. Called from biblio:process-form().
:)
declare function biblio:process-form-parameters($params as xs:string*) as element() {
    let $param := $params[1]
    let $n := substring-after($param, 'input')
    let $value := request:get-parameter($param, "")
    let $field := request:get-parameter(concat("field", $n), 'all')
    let $operator := request:get-parameter(concat("operator", $n), "and")
    return
        if (count($params) eq 1) then
            <field m="{$n}" name="{$field}">{$value}</field>
        else
            element { xs:QName($operator) } {
                biblio:process-form-parameters(subsequence($params, 2)),
                <field m="{$n}" name="{$field}">{$value}</field>
            }
};

(:~
    Process the received form parameters and create an XML representation of
    the query. Filter out empty parameters and take care of boolean operators.
:)
declare function biblio:process-form() as element(query)? {
    let $collection := request:get-parameter("collection", $config:mods-root)
    let $fields :=
        (:  Get a list of all input parameters which are not empty,
            ordered by input name. :)
        for $param in request:get-parameter-names()[starts-with(., 'input')]
        let $value := request:get-parameter($param, ())
        where string-length($value) gt 0
        order by $param descending
        return
            $param
    return
        if (exists($fields)) then
            (:  process-form recursively calls itself for every parameter and
                generates and XML representation of the query. :)
            <query>
                <collection>{$collection}</collection>
                { biblio:process-form-parameters($fields) }
            </query>
        else
            <query>
                <collection>{$collection}</collection>
            </query>
};

(:~
    Helper function used to sort by name within the "order by"
    clause of the query.
:)
declare function biblio:orderByName($m as element()) as xs:string?
{
    for $name in $m/mods:name[1]
    return
        mods:retrieve-name($name, 1)
};

(: Map order parameter to xpath for order by clause :)
declare function biblio:orderExpr($field as xs:string?) as xs:string
{
    if (sort:has-index('mods:name')) then
        if ($field eq "Score") then
            "ft:score($hit) descending"
        else if ($field = "Author") then
            "sort:index('mods:name', $hit)"
        else if ($field = "Title") then
            "sort:index('mods:title', $hit)"
        else
            "sort:index('mods:date', $hit)"
    else
        if ($field eq "Score") then
            "ft:score($hit) descending"
        else if ($field = "Author") then
            "biblio:orderByName($hit)"
        else if ($field = "Title") then
            "$hit/mods:titleInfo[1]/mods:title[1]"
        else
            "$hit/mods:originInfo/mods:dateCreated[1] descending"
};

(:~
    Evaluate the actual XPath query and order the results
:)
declare function biblio:evaluate-query($query as xs:string, $sort as xs:string?) {
    let $sortExpr := biblio:orderExpr($sort)
    let $orderedQuery :=
            concat("for $hit in ", $query, " order by ", $sortExpr, " return $hit")
    let $options :=
        <options>
            <default-operator>and</default-operator>
        </options>
    return
        util:eval($orderedQuery)
};

(:~
    Add a query to the user's query history. We store the XML representation
    of the query.
:)
declare function biblio:add-to-history($queryAsXML as element()) {
    let $oldHistory := session:get-attribute('history')
    let $newHistory :=
        let $n := if ($oldHistory) then max(for $n in $oldHistory/query/@n return xs:int($n)) + 1 else 1
        return
            <history>
                <query id="q{$n}" n="{$n}">
                    { $queryAsXML/* }
                </query>
                { $oldHistory/query }
            </history>
    return
        session:set-attribute('history', $newHistory)
};

(:~
    Retrieve a query from the query history
:)
declare function biblio:query-from-history($id as xs:string) {
    let $history := session:get-attribute('history')
    return
        $history/query[@id = $id]
};

(:~
    Returns the query history as a HTML list. The queries are
    transformed into a simple string representation.
:)
declare function biblio:query-history() {

    {
        let $history := session:get-attribute('history')
        for $query at $pos in $history/query
        return

{biblio:xml-query-to-string($query)}

    }

};

(:~
    Evaluate the query given as XML and store its results into the HTTP session
    for later reference.
:)
declare function biblio:eval-query($queryAsXML as element()?) {
    if ($queryAsXML) then
        let $query := string-join(biblio:generate-query($queryAsXML), '')
        let $log := util:log("DEBUG", ("QUERY: ", $query))
        let $sort0 := request:get-parameter("sort", ())
        let $sort := if ($sort0) then $sort0 else session:get-attribute("sort")
        let $results := biblio:evaluate-query($query, $sort)
        (:~ Take the query results and store them into the HTTP session. :)
        let $null := session:set-attribute('mods:cached', $results)
        let $null := session:set-attribute('query', $queryAsXML)
        let $null := session:set-attribute('sort', $queryAsXML)
        let $null := biblio:add-to-history($queryAsXML)
        return
            count($results)
    else
        0
};

(:~
    Clear the last query result.
:)
declare function biblio:clear() {
    let $null := session:remove-attribute('mods:cached')
    let $null := session:remove-attribute('query')
    let $null := session:remove-attribute('sort')
    return
        ()
};

(:~
    Scan the input HTML template and expand the biblio:* tags
    found therein.
:)
declare function biblio:process-templates($query as element()?, $hitCount as xs:integer?, $node as node()) {
    typeswitch ($node)
        case element(biblio:login) return
            let $user := request:get-attribute("xquery.user")
            return (
                if ($user eq 'guest') then

Login

                else

Logged in as {$user}. Logout

            )
        case element(biblio:form-from-query) return
            biblio:form-from-query($query)
        case element(biblio:result-count) return
            text { $hitCount }
        case element(biblio:query-history) return
            biblio:query-history()
        case element(biblio:collection-path) return
            let $collection := request:get-parameter("collection", $config:mods-root)
            return
                <input class="collection-input" type="text" name="collection" value="{$collection}" readonly="true"/>
        case element(biblio:form-select-current-user-groups) return
            biblio:form-select-current-user-groups($node/@name)
        case element(biblio:current-user) return
            {request:get-attribute("xquery.user")}
        case element(biblio:conditional) return
            let $result := biblio:conditional($node) return
                if($result)then
                (
                    for $child in $result/node() return
                        biblio:process-templates($query, $hitCount, $child)
                )
                else()
        case element(biblio:is-collection-owner) return
            security:is-collection-owner(security:get-user-credential-from-session()[1], request:get-parameter("collection", $config:mods-root))
        case element(biblio:has-collection-write-permissions) return
            security:can-write-collection(security:get-user-credential-from-session()[1], request:get-parameter("collection", $config:mods-root))
        case element(biblio:form-select-collection) return
            biblio:form-select-collection($node/@name)
        case element() return
            element { node-name($node) } {
                $node/@*,
                for $child in $node/node() return
                    biblio:process-templates($query, $hitCount, $child)
            }
        default return
            $node
};

declare function biblio:form-select-current-user-groups($select-name as xs:string) as element(select) {
    let $user := request:get-attribute("xquery.user") return
        <select name="{$select-name}">
        {
            for $group in xmldb:get-user-groups($user) return
                <option value="{$group}">{$group}</option>
        }
        </select>
};

declare function biblio:form-select-collection($select-name as xs:string) as element(select) {

    let $current-collection := request:get-parameter("collection", $config:mods-root) return

        <select name="{$select-name}">
        {
            if(security:can-write-collection(security:get-user-credential-from-session()[1], "/db"))then
            (
                element option {
                    if("/db" eq $current-collection)then
                    (
                        attribute selected { "selected" }
                    )else(),
                    text { "/db" }
                }
            )else(),

            for $sub-collection-path in biblio:get-writeable-subcollection-paths("/db") return
                element option {
                    if($sub-collection-path eq $current-collection)then
                    (
                        attribute selected { "selected" }
                    )else(),
                    text { $sub-collection-path }
                }
        }
        </select>
};

declare function biblio:get-writeable-subcollection-paths($path as xs:string) {

	for $sub in xmldb:get-child-collections($path)
	let $col := concat($path, "/", $sub) return
		(
			if(security:can-write-collection(security:get-user-credential-from-session()[1], $col))then
			(
			 $col
			)else(),
			biblio:get-writeable-subcollection-paths($col)
		)
};

declare function biblio:conditional($node as element(biblio:conditional)) {
    let $test-result := biblio:process-templates((), (), $node/biblio:test/biblio:*) return
        if($test-result) then
        (
            $node/biblio:result
        )else()
};

(:
declare function biblio:is-collection-owner() as xs:boolean {
    let $user := request:get-attribute("xquery.user"),
    $collection-owner := xmldb:get-owner(request:get-parameter("collection", $config:mods-root)) return
        $user eq $collection-owner
};
:)

(:
declare function biblio:has-collection-write-permissions($collection as xs:string) as xs:boolean {
	if (empty(collection($collection))) then
		false()
	else
    let $user := request:get-attribute("xquery.user"),
    $collection-permissions := xmldb:permissions-to-string(xmldb:get-permissions($collection)) return
        if(fn:matches($collection-permissions, ".......w."))then
        (
            (: world writeable :)
            true()
        )
        else if(xmldb:get-user-groups($user) = xmldb:get-group($collection) and fn:matches($collection-permissions, "....w...."))then
        (
            (: group writeable :)
            true()
        )
        else if($user eq xmldb:get-owner($collection) and fn:matches($collection-permissions, ".w......."))then
        (
            (: owner writeable :)
            true()
        )
        else
        (
            false()
        )
};
:)

(:~
    Filter an existing result set by applying an additional
    clause with "and".
:)
declare function biblio:apply-filter() {
    let $prevQuery := session:get-attribute("query")
    let $filter := request:get-parameter("filter", ())
    let $value := request:get-parameter("value", ())
    return
        if ($filter = ('All', 'Title') and count($prevQuery/field) eq 1) then
            <query>
                <field>{$prevQuery/field/@name,
                    normalize-space(concat($prevQuery/field/string(), ' ', $value))
                }</field>
            </query>
        else
            <query>
                <and>
                { $prevQuery/* }
                { <field name="{$filter}">{$value}</field> }
                </and>
            </query>
};

session:create(),
(: We receive an HTML template as input :)
let $input := request:get-data()
let $filter := request:get-parameter("filter", ())
let $history := request:get-parameter("history", ())
let $clear := request:get-parameter("clear", ())
let $mylist := request:get-parameter("mylist", ())
let $collection := request:get-parameter("collection", ())

(: Process request parameters and generate an XML representation of the query :)
let $queryAsXML :=
    if ($history) then
        biblio:query-from-history($history)
    else if ($clear) then
        biblio:clear()
    else if ($filter) then
        biblio:apply-filter()
    else if ($mylist eq 'display') then
        ()
    else
        biblio:process-form()
let $log := util:log("DEBUG", ("$queryAsXML: ", $queryAsXML))
(: Evaluate the query :)
let $results :=
    if ($mylist) then (
        if ($mylist eq 'clear') then
            session:set-attribute("personal-list", ())
        else
            (),
        let $list := session:get-attribute("personal-list")
        let $items :=
            for $item in $list/listitem
            return
                util:node-by-id(doc(substring-before($item/@id, '#')), substring-after($item/@id, '#'))
        let $null := session:set-attribute('mods:cached', $items)
        return
            count($items)
    ) else
        biblio:eval-query($queryAsXML)
(:  Process the HTML template received as input :)
let $output :=
    jquery:process(
        biblio:process-templates(if ($queryAsXML//field) then $queryAsXML else $biblio:TEMPLATE_QUERY, $results, $input)
    )
return
    $output


Changed layout to prevent unnecessary scrollbars

import module namespace template="http://cefn.com/readinglog/template" at "/home/cefn/Documents/highwire/participatory firmware design/readinglog/scripts/server/xquery/lib/template.xq";
declare default element namespace "http://www.w3.org/1999/xhtml";

declare variable $embedded external;

template:webpage(
	<iframe src="{$embedded}" style="width:98%;height:98%;">
	</iframe>
)

import module namespace template="http://cefn.com/readinglog/template" at "/home/cefn/Documents/highwire/participatory firmware design/readinglog/scripts/server/xquery/lib/template.xq";
declare default element namespace "http://www.w3.org/1999/xhtml";

declare variable $embedded external;

template:webpage(
	<iframe src="{$embedded}" width="90%" height="90%">
	</iframe>
)


Used declare namespace

Used declare namespace

svn path=/trunk/eXist-1.0/; revision=4145

declare namespace atom="http://www.w3.org/2005/Atom";
<feed xmlns="http://www.w3.org/2005/Atom">
   {
     "
",
     /atom:feed/atom:title,
     "
",
     /atom:feed/atom:id,
     "
",
     /atom:feed/atom:updated,
     "
",
     /atom:feed/atom:entry[atom:category[@scheme='http://www.smallx.com/Ontology/Atopic/2006/1/0/topic/relation' and @term='subtopic']],
     "
",
     /atom:feed/atom:link
   }
   {
      let $current := substring-before(base-uri(/atom:feed),'/.feed.atom'),
           $current-path := substring-after($current,'/db')
         return (
            <link rel="alternate" href="/atom/content{substring-after($current,'/db')}" type="application/atom+xml"/>,
           "
",
            let $parts := tokenize($current-path,'/')
               for $i in (1 to count($parts)-1)
                   let $apath := string-join(subsequence($parts,1,$i),'/'),
                       $feed := document(concat($apath,'/.feed.atom'))/atom:feed
                     return if ($feed and not($feed/atom:category[@scheme='http://www.smallx.com/Ontology/Atopic/2006/1/0/display' and @term='false']))
                       then (<entry>
                            {
                                "
",
                                $feed/atom:id,
                                "
",
                                $feed/atom:title,
                                "
",
                                $feed/atom:updated,
                                "
",
                                $feed/atom:author,
                                "
",
                                <category scheme="http://www.smallx.com/Ontology/Atopic/2006/1/0/topic/relation" term="ancestor"/>,
                                "
",
                                <link rel="alternate" href="/atom/content/{$apath}" type="application/atom+xml"/>,
                                "
",
                                <summary>
                                     {
                                         $feed/atom:subtitle/@type,
                                         $feed/atom:subtitle/node()
                                     }
                                </summary>,
                                "
"
                             }
                            </entry>,
                            "
"
                            )
                       else (),
            for $i in (collection($current)/atom:feed)
               let $path :=  substring-before(base-uri($i),'/.feed.atom'),
                   $prefix := concat($current,'/')
                  return if ($current!=$path and not(contains(substring-after($path,$prefix),'/'))
                             and not($i/atom:category[@scheme='http://www.smallx.com/Ontology/Atopic/2006/1/0/display' and @term='false']))
                     then (<entry>
                            {
                                "
",
                                $i/atom:id,
                                "
",
                                $i/atom:title,
                                "
",
                                $i/atom:updated,
                                "
",
                                <category scheme="http://www.smallx.com/Ontology/Atopic/2006/1/0/topic/relation" term="subtopic"/>,
                                "
",
                                <link rel="alternate" href="/atom/content{substring-after($path,'/db')}" type="application/atom+xml"/>,
                                "
",
                                <summary>
                                     {
                                         $i/atom:subtitle/@type,
                                         $i/atom:subtitle/node()
                                     }
                                </summary>,
                                "
"
                             }
                            </entry>,
                            "
"
                            )
                     else ()
         )
   }
</feed>

<feed xmlns="http://www.w3.org/2005/Atom"
xmlns:atom="http://www.w3.org/2005/Atom">
   {
     "
",
     /atom:feed/atom:title,
     "
",
     /atom:feed/atom:id,
     "
",
     /atom:feed/atom:updated,
     "
",
     /atom:feed/atom:entry[atom:category[@scheme='http://www.smallx.com/Ontology/Atopic/2006/1/0/topic/relation' and @term='subtopic']],
     "
",
     /atom:feed/atom:link
   }
   {
      let $current := substring-before(base-uri(/atom:feed),'/.feed.atom'),
           $current-path := substring-after($current,'/db')
         return (
            <link rel="alternate" href="/atom/content{substring-after($current,'/db')}" type="application/atom+xml"/>,
           "
",
            let $parts := tokenize($current-path,'/')
               for $i in (1 to count($parts)-1)
                   let $apath := string-join(subsequence($parts,1,$i),'/'),
                       $feed := document(concat($apath,'/.feed.atom'))/atom:feed
                     return if ($feed and not($feed/atom:category[@scheme='http://www.smallx.com/Ontology/Atopic/2006/1/0/display' and @term='false']))
                       then (<entry>
                            {
                                "
",
                                $feed/atom:id,
                                "
",
                                $feed/atom:title,
                                "
",
                                $feed/atom:updated,
                                "
",
                                $feed/atom:author,
                                "
",
                                <category scheme="http://www.smallx.com/Ontology/Atopic/2006/1/0/topic/relation" term="ancestor"/>,
                                "
",
                                <link rel="alternate" href="/atom/content/{$apath}" type="application/atom+xml"/>,
                                "
",
                                <summary>
                                     {
                                         $feed/atom:subtitle/@type,
                                         $feed/atom:subtitle/node()
                                     }
                                </summary>,
                                "
"
                             }
                            </entry>,
                            "
"
                            )
                       else (),
            for $i in (collection($current)/atom:feed)
               let $path :=  substring-before(base-uri($i),'/.feed.atom'),
                   $prefix := concat($current,'/')
                  return if ($current!=$path and not(contains(substring-after($path,$prefix),'/'))
                             and not($i/atom:category[@scheme='http://www.smallx.com/Ontology/Atopic/2006/1/0/display' and @term='false']))
                     then (<entry>
                            {
                                "
",
                                $i/atom:id,
                                "
",
                                $i/atom:title,
                                "
",
                                $i/atom:updated,
                                "
",
                                <category scheme="http://www.smallx.com/Ontology/Atopic/2006/1/0/topic/relation" term="subtopic"/>,
                                "
",
                                <link rel="alternate" href="/atom/content{substring-after($path,'/db')}" type="application/atom+xml"/>,
                                "
",
                                <summary>
                                     {
                                         $i/atom:subtitle/@type,
                                         $i/atom:subtitle/node()
                                     }
                                </summary>,
                                "
"
                             }
                            </entry>,
                            "
"
                            )
                     else ()
         )
   }
</feed>


Update BaseX database module: `db:open-id()` and `db:open-pre` changes for version 9.3; not completely sure about annotation syntax. Also updated return type occurrence indicators.

xquery version "3.1";
(:~
 : BaseX Database Module functions
 :
 : @see http://docs.basex.org/wiki/Database_Module
 :)
module namespace db = "http://basex.org/modules/db";

declare namespace a = "http://reecedunn.co.uk/xquery/annotations";
declare namespace o = "http://reecedunn.co.uk/xquery/options";

declare option o:requires "basex/7.0"; (: NOTE: 7.0 is the earliest version definitions are available for. :)

declare %a:since("basex", "7.0") function db:system() as element(system) external;
declare %a:since("basex", "9.0") function db:option($name as xs:string) as xs:string external;
declare %a:since("basex", "7.0") function db:info($db as xs:string) as element(database) external;
declare %a:since("basex", "8.6") function db:property($db as xs:string, $name as xs:string) as xs:anyAtomicType external;
declare %a:since("basex", "7.0") function db:list() as xs:string* external;
declare %a:since("basex", "7.0") function db:list($db as xs:string) as xs:string* external;
declare %a:since("basex", "7.0") function db:list($db as xs:string, $path as xs:string) as xs:string* external;
declare %a:since("basex", "7.1") function db:list-details() as element(database)* external;
declare %a:since("basex", "7.1") function db:list-details($db as xs:string) as element(resource)* external;
declare %a:since("basex", "7.1") function db:list-details($db as xs:string, $path as xs:string) as element(resource)* external;
declare %a:since("basex", "9.2") function db:dir($db as xs:string, $path as xs:string) as element()* external;
declare %a:since("basex", "7.0") function db:backups() as element(backup)* external;
declare %a:since("basex", "7.0") function db:backups($db as xs:string) as element(backup)* external;
declare %a:since("basex", "7.0") function db:open($db as xs:string) as document-node()* external;
declare %a:since("basex", "7.0") function db:open($db as xs:string, $path as xs:string) as document-node()* external;
declare %a:restrict-since("$pre", "basex", "9.3", "xs:integer*")
        %a:since("basex", "7.0") function db:open-pre($db as xs:string, $pre as xs:integer) as node()* external;
declare %a:restrict-since("$id", "basex", "9.3", "xs:integer*")
        %a:since("basex", "7.0") function db:open-id($db as xs:string, $id as xs:integer) as node()* external;
declare %a:since("basex", "7.0") function db:node-pre($nodes as node()*) as xs:integer* external;
declare %a:since("basex", "7.0") function db:node-id($nodes as node()*) as xs:integer* external;
declare %a:since("basex", "7.0") function db:retrieve($db as xs:string, $path as xs:string) as xs:base64Binary external;
declare %a:since("basex", "7.0") function db:retrieve($db as xs:string, $path as xs:string) as xs:base64Binary external;
declare %a:since("basex", "7.0") function db:text($db as xs:string, $strings as xs:string*) as text()* external;
declare %a:since("basex", "7.2.1") function db:text-range($db as xs:string, $min as xs:string, $max as xs:string) as text()* external;
declare %a:since("basex", "7.0") function db:attribute($db as xs:string, $strings as xs:string*) as attribute()* external;
declare %a:since("basex", "7.0") function db:attribute($db as xs:string, $strings as xs:string*, $name as xs:string) as attribute()* external;
declare %a:since("basex", "7.2.1") function db:attribute-range($db as xs:string, $min as xs:string, $max as xs:string) as attribute()* external;
declare %a:since("basex", "7.0") function db:attribute-range($db as xs:string, $min as xs:string, $max as xs:string, $name as xs:string) as attribute()* external;
declare %a:since("basex", "8.4") function db:token($db as xs:string, $tokens as xs:string*) as attribute()* external;
declare %a:since("basex", "8.4") function db:token($db as xs:string, $tokens as xs:string*, $name as xs:string) as attribute()* external;
declare %a:since("basex", "7.5") function db:create($db as xs:string) as empty-sequence() external;
declare %a:restrict-until("$inputs", "basex", "7.6", "item()")
        %a:since("basex", "7.5") function db:create($db as xs:string, $inputs as item()*) as empty-sequence() external;
declare %a:restrict-until("$inputs", "basex", "7.6", "item()")
        %a:restrict-until("$paths", "basex", "7.6", "xs:string")
        %a:since("basex", "7.5") function db:create($db as xs:string, $inputs as item()*, $paths as xs:string*) as empty-sequence() external;
declare %a:restrict-until("$inputs", "basex", "7.6", "item()")
        %a:restrict-until("$paths", "basex", "7.6", "xs:string")
        %a:restrict-until("$options", "basex", "8.2.1", "item()")
        %a:restrict-since("$options", "basex", "8.2.1", "map(xs:string, xs:string)")
        %a:restrict-since("$options", "basex", "8.2.3", "map(*)")
        %a:restrict-since("$options", "basex", "8.6.7", "map(*)?")
        %a:since("basex", "7.0") function db:create($db as xs:string, $inputs as item()*, $paths as xs:string*, $options as item()?) as empty-sequence() external;
declare %a:since("basex", "7.5") function db:drop($db as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:add($db as xs:string, $input as item()) as empty-sequence() external;
declare %a:restrict-since("$path", "basex", "9.2", "xs:string?")
        %a:since("basex", "7.0") function db:add($db as xs:string, $input as item(), $path as xs:string) as empty-sequence() external;
declare %a:restrict-until("$options", "basex", "8.2.1", "item()")
        %a:restrict-since("$options", "basex", "8.2.1", "map(xs:string, xs:string)")
        %a:restrict-since("$options", "basex", "8.2.3", "map(*)")
        %a:restrict-since("$options", "basex", "8.6.7", "map(*)?")
        %a:restrict-since("$path", "basex", "9.2", "xs:string?")
        %a:since("basex", "7.0") function db:add($db as xs:string, $input as item(), $path as xs:string, $options as item()?) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:delete($db as xs:string, $path as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:copy($db as xs:string, $name as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:alter($db as xs:string, $name as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:create-backup($db as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:drop-backup($name as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:restore($name as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:optimize($db as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:optimize($db as xs:string, $all as xs:boolean) as empty-sequence() external;
declare %a:restrict-until("$options", "basex", "8.2.1", "item()")
        %a:restrict-since("$options", "basex", "8.2.1", "map(xs:string, xs:string)")
        %a:restrict-since("$options", "basex", "8.2.3", "map(*)")
        %a:restrict-since("$options", "basex", "8.6.7", "map(*)?")
        %a:since("basex", "7.0") function db:optimize($db as xs:string, $all as xs:boolean, $options as item()?) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:rename($db as xs:string, $source as xs:string, $target as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:replace($db as xs:string, $path as xs:string, $input as item()) as empty-sequence() external;
declare %a:restrict-until("$options", "basex", "8.2.1", "item()")
        %a:restrict-since("$options", "basex", "8.2.1", "map(xs:string, xs:string)")
        %a:restrict-since("$options", "basex", "8.2.3", "map(*)")
        %a:restrict-since("$options", "basex", "8.6.7", "map(*)?")
        %a:since("basex", "7.0") function db:replace($db as xs:string, $path as xs:string, $input as item(), $options as item()?) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:store($db as xs:string, $path as xs:string, $input as item()) as empty-sequence() external;
declare %a:since("basex", "7.3") function db:flush($db as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.7") function db:name($node as node()) as xs:string external;
declare %a:since("basex", "7.7") function db:path($node as node()) as xs:string external;
declare %a:since("basex", "7.0") function db:exists($db as xs:string) as xs:boolean external;
declare %a:since("basex", "7.0") function db:exists($db as xs:string, $path as xs:string) as xs:boolean external;
declare %a:since("basex", "7.0") function db:is-raw($db as xs:string, $path as xs:string) as xs:boolean external;
declare %a:since("basex", "7.0") function db:is-xml($db as xs:string, $path as xs:string) as xs:boolean external;
declare %a:since("basex", "7.1") function db:content-type($db as xs:string, $path as xs:string) as xs:string external;
declare %a:since("basex", "7.2.1") %a:until("basex", "9.0") %a:see-also("basex", "9.0", "update:output") function db:output() external;
declare %a:since("basex", "8.2") %a:until("basex", "9.0") %a:see-also("basex", "9.0", "update:cache") function db:output-cache() external;
declare %a:since("basex", "7.7") function db:export($db as xs:string, $path as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.7") function db:export($db as xs:string, $path as xs:string, $params as item()) as empty-sequence() external;
declare %a:since("basex", "7.0") %a:until("basex", "8.2") function db:event($name as xs:string, $query as item()) as empty-sequence() external;
declare %a:since("basex", "7.0") %a:until("basex", "7.8") function db:fulltext($db as item(), $terms as xs:string) as text()* external;

xquery version "3.1";
(:~
 : BaseX Database Module functions
 :
 : @see http://docs.basex.org/wiki/Database_Module
 :)
module namespace db = "http://basex.org/modules/db";

declare namespace a = "http://reecedunn.co.uk/xquery/annotations";
declare namespace o = "http://reecedunn.co.uk/xquery/options";

declare option o:requires "basex/7.0"; (: NOTE: 7.0 is the earliest version definitions are available for. :)

declare %a:since("basex", "7.0") function db:system() as element(system) external;
declare %a:since("basex", "9.0") function db:option($name as xs:string) as xs:string external;
declare %a:since("basex", "7.0") function db:info($db as xs:string) as element(database) external;
declare %a:since("basex", "8.6") function db:property($db as xs:string, $name as xs:string) as xs:anyAtomicType external;
declare %a:since("basex", "7.0") function db:list() as xs:string* external;
declare %a:since("basex", "7.0") function db:list($db as xs:string) as xs:string* external;
declare %a:since("basex", "7.0") function db:list($db as xs:string, $path as xs:string) as xs:string* external;
declare %a:since("basex", "7.1") function db:list-details() as element(database)* external;
declare %a:since("basex", "7.1") function db:list-details($db as xs:string) as element(resource)* external;
declare %a:since("basex", "7.1") function db:list-details($db as xs:string, $path as xs:string) as element(resource)* external;
declare %a:since("basex", "9.2") function db:dir($db as xs:string, $path as xs:string) as element()* external;
declare %a:since("basex", "7.0") function db:backups() as element(backup)* external;
declare %a:since("basex", "7.0") function db:backups($db as xs:string) as element(backup)* external;
declare %a:since("basex", "7.0") function db:open($db as xs:string) as document-node()* external;
declare %a:since("basex", "7.0") function db:open($db as xs:string, $path as xs:string) as document-node()* external;
declare %a:since("basex", "7.0") function db:open-pre($db as xs:string, $pre as xs:integer) as node() external;
declare %a:since("basex", "7.0") function db:open-id($db as xs:string, $id as xs:integer) as node() external;
declare %a:since("basex", "7.0") function db:node-pre($nodes as node()*) as xs:integer* external;
declare %a:since("basex", "7.0") function db:node-id($nodes as node()*) as xs:integer* external;
declare %a:since("basex", "7.0") function db:retrieve($db as xs:string, $path as xs:string) as xs:base64Binary external;
declare %a:since("basex", "7.0") function db:retrieve($db as xs:string, $path as xs:string) as xs:base64Binary external;
declare %a:since("basex", "7.0") function db:text($db as xs:string, $strings as xs:string*) as text()* external;
declare %a:since("basex", "7.2.1") function db:text-range($db as xs:string, $min as xs:string, $max as xs:string) as text()* external;
declare %a:since("basex", "7.0") function db:attribute($db as xs:string, $strings as xs:string*) as attribute()* external;
declare %a:since("basex", "7.0") function db:attribute($db as xs:string, $strings as xs:string*, $name as xs:string) as attribute()* external;
declare %a:since("basex", "7.2.1") function db:attribute-range($db as xs:string, $min as xs:string, $max as xs:string) as attribute()* external;
declare %a:since("basex", "7.0") function db:attribute-range($db as xs:string, $min as xs:string, $max as xs:string, $name as xs:string) as attribute()* external;
declare %a:since("basex", "8.4") function db:token($db as xs:string, $tokens as xs:string*) as attribute()* external;
declare %a:since("basex", "8.4") function db:token($db as xs:string, $tokens as xs:string*, $name as xs:string) as attribute()* external;
declare %a:since("basex", "7.5") function db:create($db as xs:string) as empty-sequence() external;
declare %a:restrict-until("$inputs", "basex", "7.6", "item()")
        %a:since("basex", "7.5") function db:create($db as xs:string, $inputs as item()*) as empty-sequence() external;
declare %a:restrict-until("$inputs", "basex", "7.6", "item()")
        %a:restrict-until("$paths", "basex", "7.6", "xs:string")
        %a:since("basex", "7.5") function db:create($db as xs:string, $inputs as item()*, $paths as xs:string*) as empty-sequence() external;
declare %a:restrict-until("$inputs", "basex", "7.6", "item()")
        %a:restrict-until("$paths", "basex", "7.6", "xs:string")
        %a:restrict-until("$options", "basex", "8.2.1", "item()")
        %a:restrict-since("$options", "basex", "8.2.1", "map(xs:string, xs:string)")
        %a:restrict-since("$options", "basex", "8.2.3", "map(*)")
        %a:restrict-since("$options", "basex", "8.6.7", "map(*)?")
        %a:since("basex", "7.0") function db:create($db as xs:string, $inputs as item()*, $paths as xs:string*, $options as item()?) as empty-sequence() external;
declare %a:since("basex", "7.5") function db:drop($db as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:add($db as xs:string, $input as item()) as empty-sequence() external;
declare %a:restrict-since("$path", "basex", "9.2", "xs:string?")
        %a:since("basex", "7.0") function db:add($db as xs:string, $input as item(), $path as xs:string) as empty-sequence() external;
declare %a:restrict-until("$options", "basex", "8.2.1", "item()")
        %a:restrict-since("$options", "basex", "8.2.1", "map(xs:string, xs:string)")
        %a:restrict-since("$options", "basex", "8.2.3", "map(*)")
        %a:restrict-since("$options", "basex", "8.6.7", "map(*)?")
        %a:restrict-since("$path", "basex", "9.2", "xs:string?")
        %a:since("basex", "7.0") function db:add($db as xs:string, $input as item(), $path as xs:string, $options as item()?) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:delete($db as xs:string, $path as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:copy($db as xs:string, $name as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:alter($db as xs:string, $name as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:create-backup($db as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:drop-backup($name as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.8.2") function db:restore($name as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:optimize($db as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:optimize($db as xs:string, $all as xs:boolean) as empty-sequence() external;
declare %a:restrict-until("$options", "basex", "8.2.1", "item()")
        %a:restrict-since("$options", "basex", "8.2.1", "map(xs:string, xs:string)")
        %a:restrict-since("$options", "basex", "8.2.3", "map(*)")
        %a:restrict-since("$options", "basex", "8.6.7", "map(*)?")
        %a:since("basex", "7.0") function db:optimize($db as xs:string, $all as xs:boolean, $options as item()?) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:rename($db as xs:string, $source as xs:string, $target as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:replace($db as xs:string, $path as xs:string, $input as item()) as empty-sequence() external;
declare %a:restrict-until("$options", "basex", "8.2.1", "item()")
        %a:restrict-since("$options", "basex", "8.2.1", "map(xs:string, xs:string)")
        %a:restrict-since("$options", "basex", "8.2.3", "map(*)")
        %a:restrict-since("$options", "basex", "8.6.7", "map(*)?")
        %a:since("basex", "7.0") function db:replace($db as xs:string, $path as xs:string, $input as item(), $options as item()?) as empty-sequence() external;
declare %a:since("basex", "7.0") function db:store($db as xs:string, $path as xs:string, $input as item()) as empty-sequence() external;
declare %a:since("basex", "7.3") function db:flush($db as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.7") function db:name($node as node()) as xs:string external;
declare %a:since("basex", "7.7") function db:path($node as node()) as xs:string external;
declare %a:since("basex", "7.0") function db:exists($db as xs:string) as xs:boolean external;
declare %a:since("basex", "7.0") function db:exists($db as xs:string, $path as xs:string) as xs:boolean external;
declare %a:since("basex", "7.0") function db:is-raw($db as xs:string, $path as xs:string) as xs:boolean external;
declare %a:since("basex", "7.0") function db:is-xml($db as xs:string, $path as xs:string) as xs:boolean external;
declare %a:since("basex", "7.1") function db:content-type($db as xs:string, $path as xs:string) as xs:string external;
declare %a:since("basex", "7.2.1") %a:until("basex", "9.0") %a:see-also("basex", "9.0", "update:output") function db:output() external;
declare %a:since("basex", "8.2") %a:until("basex", "9.0") %a:see-also("basex", "9.0", "update:cache") function db:output-cache() external;
declare %a:since("basex", "7.7") function db:export($db as xs:string, $path as xs:string) as empty-sequence() external;
declare %a:since("basex", "7.7") function db:export($db as xs:string, $path as xs:string, $params as item()) as empty-sequence() external;
declare %a:since("basex", "7.0") %a:until("basex", "8.2") function db:event($name as xs:string, $query as item()) as empty-sequence() external;
declare %a:since("basex", "7.0") %a:until("basex", "7.8") function db:fulltext($db as item(), $terms as xs:string) as text()* external;