Browse Source

Docs: Adding Painless to the Scripting documentation.

debadair 9 years ago
parent
commit
ad28fb9ec0

+ 8 - 1
docs/reference/modules.asciidoc

@@ -45,6 +45,10 @@ The modules in this section are:
 <<modules-node,Node client>>::
 
     A Java node client joins the cluster, but doesn't hold data or act as a master node.
+    
+<<modules-scripting-painless,Painless>>::
+
+    A built-in scripting language for Elasticsearch that's designed to be as secure as possible. 
 
 <<modules-plugins,Plugins>>::
 
@@ -53,7 +57,8 @@ The modules in this section are:
 <<modules-scripting,Scripting>>::
 
     Custom scripting available in Lucene Expressions, Groovy, Python, and
-    Javascript.
+    Javascript. You can also write scripts in the built-in scripting language, 
+    <<modules-scripting-painless, Painless>>.
 
 <<modules-snapshots,Snapshot/Restore>>::
 
@@ -89,6 +94,8 @@ include::modules/network.asciidoc[]
 
 include::modules/node.asciidoc[]
 
+include::modules/painless.asciidoc[]
+
 include::modules/plugins.asciidoc[]
 
 include::modules/scripting.asciidoc[]

+ 693 - 0
docs/reference/modules/painless.asciidoc

@@ -0,0 +1,693 @@
+[[modules-scripting-painless]]
+== Painless Scripting Language
+
+_Painless_ is a simple, secure scripting language built in to Elasticsearch as a module. 
+It is designed specifically for use with Elasticsearch and can safely be used dynamically.
+
+A Painless script is essentially a single function. Painless does not provide support 
+for defining multiple functions within a script. The Painless syntax is similar to 
+http://groovy-lang.org/index.html[Groovy]. 
+
+You can use Painless anywhere a script can be used in Elasticsearch--simply set the `lang` parameter 
+to `painless`.
+
+[[painless-features]]
+[float]
+=== Painless Features
+
+* Control flow: `for` loops, `while` loops, `do/while` loops, `if/else`
+
+* Fully Typed: all available types/methods described in <<painless-api, Painless API>>
+
+* Arithmetic operators: multiplication `*`, division `/`, addition `+`, subtraction `-`, precedence `( )`
+
+* Comparison operators: less than `<`, less than or equal to `<=`, greater than `>`, greater than or equal to `>=`, equal to `==`, and not equal to `!=`, reference equals `===`, reference not equals `!==`
+
+* Boolean operators: not `!`, and `&&`, or `||`
+
+* Bitwise operators: shift left `<<`, shift right `>>`, unsigned shift `>>>`, and `&`, or `|`, xor `^`, not `~`
+
+* Shortcuts for list, map access using the dot `.` operator
+
+
+[[painless-examples]]
+[float]
+=== Painless Examples
+
+To illustrate how Painless works, let's load some hockey stats into an Elasticsearch index:
+
+[source,sh]
+----------------------------------------------------------------
+curl -XDELETE http://localhost:9200/hockey-stats
+curl -XPUT http://localhost:9200/hockey-stats
+curl -XPUT http://localhost:9200/hockey-stats/player/1 -d '{"first":"johnny", "last":"gaudreau", "goals":[9, 27, 1], "assists":[17, 46, 0], "gp":[26, 82, 1]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/2 -d '{"first":"sean", "last":"monohan", "goals":[7, 54, 26], "assists":[11, 26, 13], "gp":[26, 82, 82]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/3 -d '{"first":"jiri", "last":"hudler", "goals":[5, 34, 36], "assists":[11, 62, 42], "gp":[24, 80, 79]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/4 -d '{"first":"micheal", "last":"frolik", "goals":[4, 6, 15], "assists":[8, 23, 15], "gp":[26, 82, 82]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/5 -d '{"first":"sam", "last":"bennett", "goals":[5, 0, 0], "assists":[8, 1, 0], "gp":[26, 1, 0]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/6 -d '{"first":"dennis", "last":"wideman", "goals":[0, 26, 15], "assists":[11, 30, 24], "gp":[26, 81, 82]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/7 -d '{"first":"david", "last":"jones", "goals":[7, 19, 5], "assists":[3, 17, 4], "gp":[26, 45, 34]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/8 -d '{"first":"tj", "last":"brodie", "goals":[2, 14, 7], "assists":[8, 42, 30], "gp":[26, 82, 82]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/9 -d '{"first":"mark", "last":"giordano", "goals":[6, 30, 15], "assists":[3, 30, 24], "gp":[26, 60, 63]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/10 -d '{"first":"mikael", "last":"backlund", "goals":[3, 15, 13], "assists":[6, 24, 18], "gp":[26, 82, 82]}'
+curl -XPUT http://localhost:9200/hockey-stats/player/11 -d '{"first":"joe", "last":"colborne", "goals":[3, 18, 13], "assists":[6, 20, 24], "gp":[26, 67, 82]}'
+----------------------------------------------------------------
+
+[float]
+==== Accessing Doc Values from Painless
+
+All Painless scripts take in a `Map<String,def>` of values called `input`.  Document values can be accessed through another `Map<String,def>` within the `input` variable.  
+
+For example, the following script calculates a player's total goals. This example uses a strongly typed `int` and a `for` loop.  
+
+[source,sh]
+----------------------------------------------------------------
+curl -XGET http://localhost:9200/hockey-stats/_search -d '{
+   "query": {
+      "function_score": {
+         "script_score" : {
+            "script" : {
+               "inline": 
+                  "int total = 0; for (int i = 0; i < input.doc.goals.size(); ++i) { total += input.doc.goals[i]; } return total;", 
+               "lang": "painless"
+            }
+        }
+    }
+   }
+}'
+----------------------------------------------------------------
+
+Alternatively, you could do the same thing using a script field instead of a function score:
+
+[source,sh]
+----------------------------------------------------------------
+curl -XGET http://localhost:9200/hockey-stats/_search -d '{
+   "query": {
+      "match_all": {}}, 
+      "script_fields": {
+         "total_goals": {
+            "script": {
+               "inline": "int total = 0; for (int i = 0; i < input.doc.goals.size(); ++i) { total += input.doc.goals[i]; } return total;", 
+               "lang": "painless"
+            }
+        }
+    }
+}'
+----------------------------------------------------------------
+
+You must always specify the index of the field value you want, even if there's only a single item in the field. 
+All fields in Elasticsearch are multi-valued and Painless does not provide a `.value` shortcut. The following example uses a Painless script to sort the players by their combined first and last names. The names are accessed using
+`input.doc.first.0` and `input.doc.last.0`.  
+
+[source,sh]
+----------------------------------------------------------------
+curl -XGET http://localhost:9200/hockey-stats/_search -d '{
+   "query" : {
+      "match_all": {}}, 
+      "sort" : {
+         "_script" : {
+            "type" : "string", 
+            "script" : {"inline": "input.doc.first.0 + \" \" + input.doc.last.0", 
+            "lang": "painless"}, 
+            "order" : "asc"
+        }
+    }
+}'
+----------------------------------------------------------------
+
+[float]
+==== Updating Fields with Painless 
+
+You can also easily update fields. You access the original source for a field as `input.ctx._source.<field-name>`. 
+
+First, let's look at the source data for a player by submitting the following request:
+
+[source,sh]
+----------------------------------------------------------------
+curl -XGET http://localhost:9200/hockey-stats/_search -d '{
+   "fields" : ["_id", "_source"], "query" : {
+      "term" : { "_id" : 1 }
+    }
+}'
+----------------------------------------------------------------
+
+To change player 1's last name to _hockey_, simply set `input.ctx._source.last` to the new value:
+
+[source,sh]
+----------------------------------------------------------------
+curl -XPOST http://localhost:9200/hockey-stats/player/1/_update -d '{
+   "script": {
+      "inline": "input.ctx._source.last = input.last", 
+      "params": {"last": "hockey"}, 
+      "lang": "painless"
+   }
+}'
+----------------------------------------------------------------
+
+You can also add fields to a document. For example, this script adds a new field that contains 
+the player's nickname,  _hockey_.
+
+[source,sh]
+----------------------------------------------------------------
+curl -XPOST http://localhost:9200/hockey-stats/player/1/_update -d '{
+   "script": {
+      "inline": "input.ctx._source.last = input.last input.ctx._source.nick = input.nick", 
+      "params": {"last": "gaudreau", "nick": "hockey"}, 
+      "lang": "painless"
+   }
+}'
+----------------------------------------------------------------
+
+[float]
+==== Writing Type-Safe Scripts to Improve Performance
+
+If you explicitly specify types, the compiler doesn't have to perform type lookups at runtime, which can significantly 
+improve performance. For example, the following script performs the same first name, last name sort we showed before, 
+but it's fully type-safe.
+
+[source,sh]
+----------------------------------------------------------------
+curl -XGET http://localhost:9200/hockey-stats/_search -d '{
+   "query": {
+      "match_all": {}
+   }, 
+   "script_fields": {
+      "full_name_dynamic": {
+         "script": {
+            "inline": "def first = input.doc.first.0; def last = input.doc.last.0; return first + \" \" + last;", 
+            "lang": "painless"
+         }
+      }, 
+      "full_name_static": {
+         "script": {
+            "inline": 
+               "String first = (String)((List)((Map)input.get(\"doc\")).get(\"first\")).get(0); String last = (String)((List)((Map)input.get(\"doc\")).get(\"last\")).get(0); return first + \" \" + last;", 
+           "lang": "painless"
+         }
+       }
+    }
+}'
+----------------------------------------------------------------
+
+[[painless-api]]
+[float]
+=== Painless API
+
+The following types are available for use in the Painless language. Most types and methods map directly to their Java equivalents--for more information, see the corresponding https://docs.oracle.com/javase/8/docs/api/java/lang/package-summary.html[Javadoc].
+
+
+[float]
+==== Dynamic Types
+
+`def` (This type can be used to represent any other type.)
+
+[float]
+==== Basic Types
+
+`void`
+
+`boolean`
+
+`short`
+
+`char`
+
+`int`
+
+`long`
+
+`float`
+
+`double`
+
+[float]
+==== Complex Types
+
+Non-static methods/members in superclasses are available to subclasses.
+Generic types with unspecified generic parameters are parameters of type `def`.
+
+-----
+ArithmeticException extends Exception
+   <init>()
+-----
+
+-----
+ArrayList extends List
+   <init>()
+-----
+
+-----
+ArrayList<Object> extends List<Object>
+   <init>()
+-----
+
+-----
+ArrayList<String> extends List<String>    
+    <init>()
+-----
+
+-----
+Boolean extends Object
+   <init>(boolean)
+   static Boolean valueOf(boolean)
+   boolean booleanValue()
+-----
+
+-----
+Character extends Object    
+    <init>(char)
+    static Character valueOf(char)
+    char charValue()
+    static char MIN_VALUE
+    static char MAX_VALUE
+-----    
+
+-----
+CharSequence extends Object
+    char charAt(int)
+    int length()
+-----
+
+-----
+Collection extends Object
+    boolean add(def)
+    void clear()
+    boolean contains(def)
+    boolean isEmpty()
+    Iterator iterator()
+    boolean remove(def)
+    int size()
+-----
+
+-----
+Collection<Object> extends Object
+    boolean add(Object)
+    void clear()
+    boolean contains(Object)
+    boolean isEmpty()
+    Iterator iterator()
+    boolean remove(Object)
+    int size()
+-----
+
+-----
+Collection<String> extends Object
+    boolean add(String)
+    void clear()
+    boolean contains(String)
+    boolean isEmpty()
+    Iterator iterator()
+    boolean remove(String)
+    int size()
+-----
+
+-----
+Double extends Number
+    <init>(double)
+    static Double valueOf(double)
+    static double MIN_VALUE
+    static double MAX_VALUE
+-----
+
+-----
+Exception extends Object
+    String getMessage()    
+-----
+
+-----
+Float extends Number
+    <init>(float)
+    static Float valueOf(float)
+    static float MIN_VALUE
+    static float MAX_VALUE
+-----
+
+-----
+HashMap extends Map
+    <init>()    
+-----
+
+-----
+HashMap<Object,Object> extends Map<Object,Object>
+    <init>()
+-----
+
+-----
+HashMap<String,def> extends Map<String,def>
+    <init>()    
+-----
+
+-----
+HashMap<String,Object> extends Map<String,Object>
+    <init>()
+-----
+    
+-----
+IllegalArgument extends Exception
+    <init>()
+-----
+
+-----
+IllegalState extends Exception
+    <init>()    
+-----
+
+-----
+Integer extends Number
+    <init>(int)
+    static Integer valueOf(int)
+    static int MIN_VALUE
+    static int MAX_VALUE
+-----
+
+-----
+Iterator extends Object
+    boolean hasNext()
+    def next()
+    void remove()
+-----
+
+-----
+Iterator<String> extends Object
+    boolean hasNext()
+    String next()
+    void remove()
+-----
+
+-----
+List extends Collection
+    def set(int, def)
+    def get(int)
+    def remove(int)
+-----
+
+-----
+List<Object> extends Collection
+    Object set(int, Object)
+    Object get(int)
+    Object remove(int)
+-----
+
+-----
+List<String> extends Collection
+    String set(int, String)
+    String get(int)
+    String remove(int)
+-----
+
+-----
+Long extends Number
+    <init>(long)
+    static Long valueOf(long)
+    static long MIN_VALUE
+    static long MAX_VALUE
+-----
+
+-----
+Map extends Object
+    def put (def, def)
+    def get (def)
+    def remove (def)
+    boolean isEmpty()
+    int size()
+    boolean containsKey(def)
+    boolean containsValue(def)
+    Set keySet()
+    Collection values()    
+-----
+
+-----
+Map<Object,Object> extends Object
+    Object put (Object, Object)
+    Object get (Object)
+    Object remove (Object)
+    boolean isEmpty()
+    int size()
+    boolean containsKey(Object)
+    boolean containsValue(Object)
+    Set keySet()
+    Collection values()
+-----
+
+-----
+Map<String,def> extends Object
+    def put (String, def)
+    def get (String)
+    def remove (String)
+    boolean isEmpty()
+    int size()
+    boolean containsKey(String)
+    boolean containsValue(def)
+    Set<String> keySet()
+    Collection values()
+-----
+
+-----
+Map<String,Object> extends Object
+    Object put (String, Object)
+    Object get (String)
+    Object remove (String)
+    boolean isEmpty()
+    int size()
+    boolean containsKey(String)
+    boolean containsValue(Object)
+    Set<String> keySet()
+    Collection values()
+-----
+
+-----
+Number extends Object
+    short shortValue()
+    short shortValue()
+    int intValue()
+    long longValue()
+    float floatValue()
+    double doubleValue()
+-----
+
+-----
+Object
+    String toString()
+    boolean equals(Object)
+    int hashCode()
+-----
+
+-----
+Set extends Collection
+-----
+
+-----
+Set<Object> extends Collection<Object>
+-----
+
+-----
+Set<String> extends Collection<String>
+-----
+
+-----
+Short extends Number
+    <init>(short)
+    static Short valueOf(short)
+    static short MIN_VALUE
+    static short MAX_VALUE
+-----
+
+-----
+String extends CharSequence
+    <init>(String)
+    int codePointAt(int)
+    int compareTo(String)
+    String concat(String)
+    boolean endsWith(String)
+    int indexOf(String, int)
+    boolean isEmpty()
+    String replace(CharSequence, CharSequence)
+    boolean startsWith(String)
+    String substring(int, int)
+    char[] toCharArray()
+    String trim()
+-----
+
+-----
+NumberFormatException extends Exception
+    <init>()
+-----
+
+-----
+Void extends Object
+-----
+
+[float]
+==== Utility Classes
+
+-----
+Math
+   static double abs(double)
+   static float fabs(float)
+   static long labs(long)
+   static int iabs(int)
+   static double acos(double)
+   static double asin(double)
+   static double atan(double)
+   static double atan2(double)
+   static double cbrt(double)
+   static double ceil(double)
+   static double cos(double)
+   static double cosh(double)
+   static double exp(double)
+   static double expm1(double)
+   static double floor(double)
+   static double hypt(double, double)
+   static double abs(double)
+   static double log(double)
+   static double log10(double)
+   static double log1p(double)
+   static double max(double, double)
+   static float fmax(float, float)
+   static long lmax(long, long)
+   static int imax(int, int)
+   static double min(double, double)
+   static float fmin(float, float)
+   static long lmin(long, long)
+   static int imin(int, int)   
+   static double pow(double, double)
+   static double random()
+   static double rint(double)
+   static long round(double)
+   static double sin(double)
+   static double sinh(double)
+   static double sqrt(double)
+   static double tan(double)
+   static double tanh(double)
+   static double toDegrees(double)
+   static double toRadians(double)
+-----
+
+-----
+Utility
+   static boolean NumberToboolean(Number)
+   static char NumberTochar(Number)
+   static Boolean NumberToBoolean(Number)
+   static Short NumberToShort(Number)
+   static Character NumberToCharacter(Number)
+   static Integer NumberToInteger(Number)
+   static Long NumberToLong(Number)
+   static Float NumberToFloat(Number)
+   static Double NumberToDouble(Number)
+   static byte booleanTobyte(boolean)
+   static short booleanToshort(boolean)
+   static char booleanTochar(boolean)
+   static int booleanToint(boolean)
+   static long booleanTolong(boolean)
+   static float booleanTofloat(boolean)
+   static double booleanTodouble(boolean)
+   static Integer booleanToInteger(boolean)
+   static byte BooleanTobyte(Boolean)
+   static short BooleanToshort(Boolean)
+   static char BooleanTochar(Boolean)
+   static int BooleanToint(Boolean)
+   static long BooleanTolong(Boolean)
+   static float BooleanTofloat(Boolean)
+   static double BooleanTodouble(Boolean)
+   static Byte BooleanToByte(Boolean)
+   static Short BooleanToShort(Boolean)
+   static Character BooleanToCharacter(Boolean)
+   static Integer BooleanToInteger(Boolean)
+   static Long BooleanToLong(Boolean)
+   static Float BooleanToFloat(Boolean)
+   static Double BooleanToDouble(Boolean)
+   static boolean byteToboolean(byte)
+   static Short byteToShort(byte)
+   static Character byteToCharacter(byte)
+   static Integer byteToInteger(byte)
+   static Long byteToLong(byte)
+   static Float byteToFloat(byte)
+   static Double byteToDouble(byte)
+   static boolean ByteToboolean(Byte)
+   static char ByteTochar(Byte)
+   static boolean shortToboolean(short)
+   static Byte shortToByte(short)
+   static Character shortToCharacter(short)
+   static Integer shortToInteger(short)
+   static Long shortToLong(short)
+   static Float shortToFloat(short)
+   static Double shortToDouble(short)
+   static boolean ShortToboolean(Short)
+   static char ShortTochar(Short)
+   static boolean charToboolean(char)
+   static Byte charToByte(char)
+   static Short charToShort(char)
+   static Integer charToInteger(char)
+   static Long charToLong(char)
+   static Float charToFloat(char)
+   static Double charToDouble(char)
+   static boolean CharacterToboolean(Character)
+   static byte CharacterTobyte(Character)
+   static short CharacterToshort(Character)
+   static int CharacterToint(Character)
+   static long CharacterTolong(Character)
+   static float CharacterTofloat(Character)
+   static double CharacterTodouble(Character)
+   static Boolean CharacterToBoolean(Character)
+   static Byte CharacterToByte(Character)
+   static Short CharacterToShort(Character)
+   static Integer CharacterToInteger(Character)
+   static Long CharacterToLong(Character)
+   static Float CharacterToFloat(Character)
+   static Double CharacterToDouble(Character)
+   static boolean intToboolean(int)
+   static Byte intToByte(int)
+   static Short intToShort(int)
+   static Character intToCharacter(int)
+   static Long intToLong(int)
+   static Float intToFloat(int)
+   static Double intToDouble(int)
+   static boolean IntegerToboolean(Integer)
+   static char IntegerTochar(Integer)
+   static boolean longToboolean(long)
+   static Byte longToByte(long)
+   static Short longToShort(long)
+   static Character longToCharacter(long)
+   static Integer longToInteger(long)
+   static Float longToFloat(long)
+   static Double longToDouble(long)
+   static boolean LongToboolean(Long)
+   static char LongTochar(Long)
+   static boolean floatToboolean(float)
+   static Byte floatToByte(float)
+   static Short floatToShort(float)
+   static Character floatToCharacter(float)
+   static Integer floatToInteger(float)
+   static Long floatToLong(float)
+   static Double floatToDouble(float)
+   static boolean FloatToboolean(Float)
+   static char FloatTochar(Float)
+   static boolean doubleToboolean(double)
+   static Byte doubleToByte(double)
+   static Short doubleToShort(double)
+   static Character doubleToCharacter(double)
+   static Integer doubleToInteger(double)
+   static Long doubleToLong(double)
+   static Float doubleToFloat(double)
+   static boolean DoubleToboolean(Double)
+   static char DoubleTochar(Double)
+-----
+
+-----
+Def
+    static boolean defToboolean(def)
+    static byte defTobyte(def)
+    static short defToshort(def)
+    static char defTochar(def)
+    static int defToint(def)
+    static long defTolong(def)
+    static float defTofloat(def)
+    static double defTodouble(def)
+    static Boolean defToBoolean(def)
+    static Byte defToByte(def)
+    static Character defToCharacter(def)
+    static Integer defToInteger(def)
+    static Long defToLong(def)
+    static Float defToFloat(def)
+    static Double defToDouble(def)
+-----

+ 0 - 1
docs/reference/modules/scripting.asciidoc

@@ -3,4 +3,3 @@ include::scripting/scripting.asciidoc[]
 include::scripting/advanced-scripting.asciidoc[]
 
 include::scripting/security.asciidoc[]
-

+ 39 - 39
docs/reference/modules/scripting/scripting.asciidoc

@@ -1,27 +1,48 @@
 [[modules-scripting]]
 == Scripting
 
-The scripting module allows to use scripts in order to evaluate custom
-expressions. For example, scripts can be used to return "script fields"
-as part of a search request, or can be used to evaluate a custom score
-for a query and so on.
+The scripting module enables you to use scripts to evaluate custom
+expressions. For example, you could use a script to return "script fields"
+as part of a search request or evaluate a custom score for a query.
 
-The scripting module uses by default http://groovy-lang.org/[groovy]
-(previously http://mvel.codehaus.org/[mvel] in 1.3.x and earlier) as the
-scripting language with some extensions. Groovy is used since it is extremely
-fast and very simple to use.
+TIP: Elasticsearch now has a built-in scripting language called _Painless_
+that provides a more secure alternative for implementing
+scripts for Elasticsearch. We encourage you to try it out--
+for more information, see <<modules-scripting-painless, Painless Scripting Language>>.
+
+The default scripting language is http://groovy-lang.org/[groovy] 
+(http://mvel.codehaus.org/[mvel] was the default in 1.3.x and earlier). 
+
+Additional `lang` plugins enable you to run scripts written in other languages. 
+Everywhere a script can be used, you can include a `lang` parameter
+to specify the language of the script. Plugins are available for following languages:
+
+[cols="<,<,<",options="header",]
+|=======================================================================
+|Language   |Sandboxed |Required plugin
+|groovy     |no        |built-in
+|expression |yes       |built-in
+|mustache   |yes       |built-in
+/painless   /yes       /built-in (module)
+|javascript |no        |{plugins}/lang-javascript.html[elasticsearch-lang-javascript]
+|python     |no        |{plugins}/lang-python.html[elasticsearch-lang-python]
+|=======================================================================
 
 .Groovy dynamic scripting off by default from v1.4.3
 [IMPORTANT]
 ===================================================
 
-Groovy dynamic scripting is off by default, preventing dynamic Groovy scripts
-from being accepted as part of a request or retrieved from the special
-`.scripts` index. You will still be able to use Groovy scripts stored in files
-in the `config/scripts/` directory on every node.
+Groovy dynamic scripting is off by default. This prevents Groovy scripts
+from being accepted as part of a request or retrieved from the 
+`.scripts` index. You can still use Groovy file scripts stored in 
+the `config/scripts/` directory on every node.
 
-To convert an inline script to a file, take this simple script
-as an example:
+To convert an inline script to a file-based script, save the contents
+of the `inline` field to a file with the `.groovy` extension and
+store it in the `config/scripts` directory on every data node in your
+cluster. 
+
+For example, if you have the following inline script:
 
 [source,js]
 -----------------------------------
@@ -38,15 +59,9 @@ GET /_search
 }
 -----------------------------------
 
-Save the contents of the `inline` field as a file called `config/scripts/my_script.groovy`
-on every data node in the cluster:
+Save `1 + my_var` in a file called `config/scripts/my_script.groovy`.
 
-[source,js]
------------------------------------
-1 + my_var
------------------------------------
-
-Now you can access the script by file name (without the extension):
+To use the script in a request, specify its name (without the `.groovy` extension) in the `file` field:
 
 [source,js]
 -----------------------------------
@@ -67,21 +82,8 @@ GET /_search
 
 ===================================================
 
-
-Additional `lang` plugins are provided to allow to execute scripts in
-different languages. All places where a script can be used, a `lang` parameter
-can be provided to define the language of the script. The following are the
-supported scripting languages:
-
-[cols="<,<,<",options="header",]
-|=======================================================================
-|Language   |Sandboxed |Required plugin
-|groovy     |no        |built-in
-|expression |yes       |built-in
-|mustache   |yes       |built-in
-|javascript |no        |{plugins}/lang-javascript.html[elasticsearch-lang-javascript]
-|python     |no        |{plugins}/lang-python.html[elasticsearch-lang-python]
-|=======================================================================
+[float]
+=== File-based Scripts
 
 To increase security, Elasticsearch does not allow you to specify scripts for
 non-sandboxed languages with a request. Instead, scripts must be placed in the
@@ -219,8 +221,6 @@ Indexed scripts can be deleted by:
 curl -XDELETE localhost:9200/_scripts/groovy/indexedCalculateScore
 -----------------------------------
 
-
-
 [float]
 [[enable-dynamic-scripting]]
 === Enabling dynamic scripting