Search code examples
dictionaryxquerymarklogic

Creating a global map variable in xquery library module in Marklogic


I need to add a map to a library module. The map's used by most of its functions. I have a function that populates the map.

declare variable $map as map:map :=local:populateMap();

declare function local:populateMap() {
  let $map:=map:map()
   let $dummy1:=for $id in cts:search(/document/id,cts:element-query(xs:QName("document"),cts:and-query(())),"unfiltered" )
      let $dummy2:=map:put($map,$id/fn:string(),someValueCorrespondingToCurrentId)
       return ()
   return $map     

};

other functions that use the map

My documents look like this:

<document>
 <id>id</id>
<otherElements>
 ...........
</otherElements> 
</document>

The code inside local:populateMap() looks a bit awkward to me especially for the use of those dummy variables. What would be a better approach to do this?


Solution

  • Suppose you have a path range index on /document/id:

    declare function local:populateMap() {
      map:new((
        cts:values(
          cts:path-reference("/document/id"))
        ) ! map:entry(., someValueCorrespondingToCurrentId)
      ))
    };
    

    Suppose someValueCorrespondingToCurrentId is something that comes from the same document as the id and also has a range index on it.

    declare function local:populateMap() {
      map:new((
        cts:values(cts:path-reference("/document/id"))) ! 
          map:entry(., 
            cts:values(
              cts:SOMETHING-reference(
                reference-spec, 
                (), 
                "limit=1", 
                cts:path-range-query("/document/id", "=", .)
              )
            )
          )
      ))
    };
    

    The "!" operator concisely replaces your inner FLWOR, while map:new and map:entry replace the outer one. In the second code block above, I'm looking up the cts:*-reference that occurs in the same document as the current id. In both cases, all values are retrieved from indexes, so documents don't need to be loaded from disk.