Browse Source

Painless Context Doc: Add field context example (#35130)

* Painless Context Doc: Add field context example

relates to #34829
Mayya Sharipova 7 years ago
parent
commit
7e144b318a

+ 56 - 0
docs/painless/painless-contexts/painless-field-context.asciidoc

@@ -26,3 +26,59 @@ a customized value for each document in the results of a query.
 *API*
 
 The standard <<painless-api-reference, Painless API>> is available.
+
+
+*Example*
+
+To run this example, first follow the steps in
+<<painless-context-examples, context examples>>.
+
+You can then use these two example scripts to compute custom information
+for each search hit and output it to two new fields.
+
+The first script gets the doc value for the `datetime` field and calls
+the `getDayOfWeek` function to determine the corresponding day of the week.
+
+[source,Painless]
+----
+doc['datetime'].value.getDayOfWeek();
+----
+
+The second script calculates the number of actors. Actors' names are stored
+as a text array in the `actors` field.
+
+[source,Painless]
+----
+params['_source']['actors'].length;                        <1>
+----
+
+<1> By default, doc values are not available for text fields. However,
+    you can still calculate the number of actors by extracting actors
+    from `_source`. Note that `params['_source']['actors']` is a list.
+
+
+Submit the following request:
+
+[source,js]
+----
+GET seats/_search
+{
+    "query" : {
+        "match_all": {}
+    },
+    "script_fields" : {
+        "day-of-week" : {
+            "script" : {
+                "source": "doc['datetime'].value.getDayOfWeek()"
+            }
+        },
+        "number-of-actors" : {
+            "script" : {
+                "source": "params['_source']['actors'].length"
+            }
+        }
+    }
+}
+----
+// CONSOLE
+// TEST[skip: requires setup from other pages]

+ 52 - 0
modules/lang-painless/src/test/java/org/elasticsearch/painless/ContextExampleTests.java

@@ -19,6 +19,11 @@
 
 package org.elasticsearch.painless;
 
+import java.util.HashMap;
+import java.util.Map;
+
+import static java.util.Collections.singletonMap;
+
 /**
  * These tests run the Painless scripts used in the context docs against
  * slightly modified data designed around unit tests rather than a fully-
@@ -308,4 +313,51 @@ public class ContextExampleTests extends ScriptTestCase {
     curl -XPOST localhost:9200/seats/seat/_bulk?pipeline=seats -H "Content-Type: application/x-ndjson" --data-binary "@/home/jdconrad/test/seats.json"
 
     */
+
+
+    // Use script_fields API to add two extra fields to the hits
+
+    /*
+    curl -X GET localhost:9200/seats/_search
+    {
+        "query" : {
+            "match_all": {}
+        },
+        "script_fields" : {
+            "day-of-week" : {
+                "script" : {
+                    "source": "doc['datetime'].value.getDayOfWeek()"
+                }
+            },
+            "number-of-actors" : {
+                "script" : {
+                    "source": "params['_source']['actors'].length"
+                }
+            }
+        }
+    }
+    */
+
+
+    // Testing only params, as I am not sure how to test Script Doc Values in painless
+    public void testScriptFieldsScript() {
+        Map<String, Object> hit = new HashMap<>();
+        Map<String, Object> fields = new HashMap<>();
+        fields.put("number-of-actors", 4);
+        hit.put("fields", fields);
+
+        Map<String, Object> source = new HashMap<>();
+        String[] actors =  {"James Holland", "Krissy Smith", "Joe Muir", "Ryan Earns"};
+        source.put("actors", actors);
+
+        assertEquals(hit, exec(
+            "Map fields = new HashMap();" +
+                "fields[\"number-of-actors\"] = params['_source']['actors'].length;" +
+                "Map rtn = new HashMap();" +
+                "rtn[\"fields\"] = fields;" +
+                "return rtn;",
+            singletonMap("_source", source), true)
+        );
+    }
 }
+