Author: yonik
Date: Thu Mar  5 20:33:51 2009
New Revision: 750577

URL: http://svn.apache.org/viewvc?rev=750577&view=rev
Log:
SOLR-1046: Nested query support for function query parser

Modified:
    lucene/solr/trunk/CHANGES.txt
    lucene/solr/trunk/src/java/org/apache/solr/search/FunctionQParser.java
    
lucene/solr/trunk/src/test/org/apache/solr/search/function/TestFunctionQuery.java

Modified: lucene/solr/trunk/CHANGES.txt
URL: 
http://svn.apache.org/viewvc/lucene/solr/trunk/CHANGES.txt?rev=750577&r1=750576&r2=750577&view=diff
==============================================================================
--- lucene/solr/trunk/CHANGES.txt (original)
+++ lucene/solr/trunk/CHANGES.txt Thu Mar  5 20:33:51 2009
@@ -175,6 +175,11 @@
 
 28. SOLR-739: Add support for OmitTf (Mark Miller via yonik)
 
+29. SOLR-1046: Nested query support for the function query parser
+    and lucene query parser (the latter existed as an undocumented 
+    feature in 1.3) (yonik)
+
+
 Optimizations
 ----------------------
  1. SOLR-374: Use IndexReader.reopen to save resources by re-using parts of the

Modified: lucene/solr/trunk/src/java/org/apache/solr/search/FunctionQParser.java
URL: 
http://svn.apache.org/viewvc/lucene/solr/trunk/src/java/org/apache/solr/search/FunctionQParser.java?rev=750577&r1=750576&r2=750577&view=diff
==============================================================================
--- lucene/solr/trunk/src/java/org/apache/solr/search/FunctionQParser.java 
(original)
+++ lucene/solr/trunk/src/java/org/apache/solr/search/FunctionQParser.java Thu 
Mar  5 20:33:51 2009
@@ -123,19 +123,17 @@
     
     if (sp.opt("$")) {
       String param = sp.getId();
-      sp.pos += param.length();
       String qstr = getParam(param);
       qstr = qstr==null ? "" : qstr;
-      nestedQuery = subQuery(qstr, null).parse();
+      nestedQuery = subQuery(qstr, null).getQuery();
     }
     else {
       int start = sp.pos;
-      int end = sp.pos;
-      String v = sp.val; 
+      String v = sp.val;
   
-      String qs = v.substring(start);
+      String qs = v;
       HashMap nestedLocalParams = new HashMap<String,String>();
-      end = QueryParsing.parseLocalParams(qs, start, nestedLocalParams, 
getParams());
+      int end = QueryParsing.parseLocalParams(qs, start, nestedLocalParams, 
getParams());
   
       QParser sub;
   
@@ -143,7 +141,7 @@
         if (nestedLocalParams.get(QueryParsing.V) != null) {
           // value specified directly in local params... so the end of the
           // query should be the end of the local params.
-          sub = subQuery(qs.substring(0, end), null);
+          sub = subQuery(qs.substring(start, end), null);
         } else {
           // value here is *after* the local params... ask the parser.
           sub = subQuery(qs, null);

Modified: 
lucene/solr/trunk/src/test/org/apache/solr/search/function/TestFunctionQuery.java
URL: 
http://svn.apache.org/viewvc/lucene/solr/trunk/src/test/org/apache/solr/search/function/TestFunctionQuery.java?rev=750577&r1=750576&r2=750577&view=diff
==============================================================================
--- 
lucene/solr/trunk/src/test/org/apache/solr/search/function/TestFunctionQuery.java
 (original)
+++ 
lucene/solr/trunk/src/test/org/apache/solr/search/function/TestFunctionQuery.java
 Thu Mar  5 20:33:51 2009
@@ -100,9 +100,20 @@
     return sb.toString();
   }
 
-  void singleTest(String field, String funcTemplate, float... results) {
-    // lrf.args.put("version","2.0");
+  void singleTest(String field, String funcTemplate, List<String> args, 
float... results) {
     String parseableQuery = func(field, funcTemplate);
+
+    List<String> nargs = new ArrayList<String>(Arrays.asList("q", 
parseableQuery
+            ,"fl", "*,score"
+            ,"indent","on"
+            ,"rows","100"));
+
+    if (args != null) {
+      for (String arg : args) {
+        nargs.add(arg.replace("\0",field));
+      }
+    }
+
     List<String> tests = new ArrayList<String>();
 
     // Construct xpaths like the following:
@@ -115,11 +126,13 @@
       tests.add(xpath);
     }
 
-    assertQ(req("q", parseableQuery
-                ,"fl", "*,score","indent","on","rows","100"
-                )
-            , tests.toArray(new String[tests.size()])
-            );
+    assertQ(req(nargs.toArray(new String[]{}))
+            , tests.toArray(new String[]{})
+    );
+  }
+
+  void singleTest(String field, String funcTemplate, float... results) {
+    singleTest(field, funcTemplate, null, results);
   }
 
   void doTest(String field) {
@@ -128,6 +141,7 @@
       100,-4,0,10,25,5
     };
     createIndex(field,vals);
+    createIndex(null, 88);  // id with no value
 
     // test identity (straight field value)
     singleTest(field, "\0", 10,10);
@@ -168,6 +182,18 @@
     
     // compose the ValueSourceParser plugin function with another function
     singleTest(field, "nvl(sum(0,\0),1)", 0, 1, 100, 100);
+
+    // test simple embedded query
+    singleTest(field,"query({!func v=\0})", 10, 10, 88, 0);
+    // test default value for embedded query
+    singleTest(field,"query({!lucene v='\0:[* TO *]'},8)", 88, 8);
+    singleTest(field,"sum(query({!func v=\0},7.1),query({!func v=\0}))", 10, 
20, 100, 200);
+    // test with sub-queries specified by other request args
+    singleTest(field,"query({!func v=$vv})", Arrays.asList("vv","\0"), 10, 10, 
88, 0);
+    singleTest(field,"query($vv)",Arrays.asList("vv","{!func}\0"), 10, 10, 88, 
0);
+    singleTest(field,"sum(query($v1,5),query($v1,7))",
+            Arrays.asList("v1","\0:[* TO *]"),  88,12
+            );
   }
 
   public void testFunctions() {


Reply via email to