不管Elasticsearch API支持何种脚本,语法都遵循相同的模式:express
"script": { "lang": "...", "source" | "id": "...", "params": { ... } }
painless
。source
或存储脚本的id
。例如,在搜索请求中使用如下脚原本返回脚本字段:segmentfault
PUT my_index/_doc/1 { "my_field": 5 } GET my_index/_search { "script_fields": { "my_doubled_field": { "script": { "lang": "expression", "source": "doc['my_field'] * multiplier", "params": { "multiplier": 2 } } } } }
lang
缓存
painless
。source
,id
less
inline
脚本是指定source
,如上例所示,存储的脚本是指定的id
,并从群集状态中检索(请参阅存储的脚本)。params
ui
Elasticsearch第一次看到一个新脚本,它会编译它并将编译后的版本存储在缓存中,编译多是一个繁重的过程。
若是须要将变量传递给脚本,则应将它们做为命名参数传递给脚本自己而不是硬编码值,例如,若是你但愿可以将字段值乘以不一样的乘数,请不要将乘数硬编码到脚本中:编码
"source": "doc['my_field'] * 2"
相反,将其做为命名参数传递:code
"source": "doc['my_field'] * multiplier", "params": { "multiplier": 2 }
第一个版本每次乘数改变时都必须从新编译,第二个版本只编译一次。对象
若是你在很短的时间内编译了太多独特的脚本,Elasticsearch将使用circuit_breaking_exception
错误拒绝新的动态脚本。默认状况下,每分钟将编译最多15个内联脚本,你能够经过设置script.max_compilations_rate
动态更改此设置。ip
可使用简短脚本形式来简化,在简短形式中,script
由字符串而不是对象表示,该字符串包含脚本的源。ci
简写:
"script": "ctx._source.likes++"
正常形式的相同脚本:
"script": { "source": "ctx._source.likes++" }
可使用_scripts
端点将脚本存储在集群状态中并从集群状态中检索脚本。
如下是使用位于/_scripts/{id}
的存储脚本的示例。
首先,在集群状态下建立名为calculate-score
的脚本:
POST _scripts/calculate-score { "script": { "lang": "painless", "source": "Math.log(_score * 2) + params.my_modifier" } }
可使用如下命令检索相同的脚本:
GET _scripts/calculate-score
能够经过指定id
参数来使用存储的脚本,以下所示:
GET _search { "query": { "script": { "script": { "id": "calculate-score", "params": { "my_modifier": 2 } } } } }
删除:
DELETE _scripts/calculate-score
默认状况下,全部脚本都被缓存,所以只有在更新发生时才须要从新编译它们,默认状况下,脚本没有基于时间的过时,但你可使用script.cache.expire
设置更改此行为,你可使用script.cache.max_size
设置配置此缓存的大小,默认状况下,缓存大小为100
。
存储脚本的大小限制为65,535字节,这能够经过设置
script.max_size_in_bytes
设置来增长软限制来更改,但若是脚本很是大,则应考虑原生脚本引擎。