user1660340
user1660340

Reputation: 131

Marklogic : Wilcard search on Element range Index with search:search

Page1.xml

<pages xmlns="http://marklogic.com/docs">
  <page>
    <elementNode>data1</elementNode>
    <textNode>text1</textNode>
  </page>
  <page>
    <elementNode>data2</elementNode>
    <textNode>text2</textNode>
  </page>
  <page>
    <elementNode>data3</elementNode>
    <textNode>text3</textNode>
  </page>
  <page>
    <elementNode>data4</elementNode>
    <textNode>text4</textNode>
  </page>
</pages>

I have created an element range index on elementNode, then executed the following XQuery:

xquery version "1.0-ml";
declare namespace html = "http://www.w3.org/1999/xhtml";
declare namespace ts= "http://marklogic.com/docs";
import module namespace search ="http://marklogic.com/appservices/search" at "/MarkLogic/appservices/search/search.xqy";

declare variable $options :=  
  <options xmlns="http://marklogic.com/appservices/search">
    <searchable-expression xmlns:ex="http://marklogic.com/docs">//ex:page</searchable-expression>
    <grammar>
      <starter strength="30" apply="grouping" delimiter=")">(</starter>
      <starter strength="40" apply="prefix" element="cts:not-query">NOT</starter>
      <joiner strength="10" apply="infix" element="cts:or-query" tokenize="word">OR</joiner>
      <joiner strength="20" apply="infix" element="cts:and-query" tokenize="word">AND</joiner>
      <joiner strength="50" apply="constraint">:</joiner>
    </grammar>
    <constraint name="elementNode">
      <range collation="http://marklogic.com/collation/" type="xs:string">
        <facet-option>limit=1000</facet-option>
        <element ns="http://marklogic.com/docs" name="elementNode"/>
        <searchable-expression xmlns:ex="http://marklogic.com/clover/docs-xml">//ex:elementNode</searchable-expression>
      </range>
    </constraint>
  </options>;

let $searchResult := search:search("elementNode:(*data*)", $options)
return $searchResult

In the above case I am not getting any result because I have used wild card asterisk [*] here. Is there any way to enable wild card search with element range constraints? Thanks in advance.

Upvotes: 1

Views: 1090

Answers (1)

wst
wst

Reputation: 11771

Range constraints use cts:element-range-query(), which allows for value comparison but not wildcards. However, cts:element-value-match() is designed to use wildcard expressions, so one solution is to build a custom constraint with that API call:

declare function parse(
    $constraint-qtext as xs:string,
    $right as schema-element(cts:query))
as schema-element(cts:query)
{
    let $vals := cts:element-value-match(
        xs:QName("elementNode"),
        string($right//cts:text))
    return document { 
        cts:element-range-query(xs:QName("elementNode"),"=",$vals) }/*
};

And then declare that in your options node:

<options xmlns="http://marklogic.com/appservices/search">
    <constraint name="match-elementName">
        <custom facet="false">
            <parse apply="parse" ns="" at="/custom.xqy"/>
        </custom>
    </constraint>
</options>

If you don't need the range index, though, it might be simpler to create a field over elementNode and then use a field constraint:

<constraint name="elementNode">
    <term-option>wildcarded</term-option>
    <word>
        <field name="field-elementNode"/>
    </word>
</constraint>

Upvotes: 2

Related Questions