[7.x] Move internal index templates to composable templates (#61457) (#61661)

This change moves watcher, ILM history and SLM history templates to composable templates.
Versions are updated to reflect the switch. Only change to the templates themselves is added `_meta` to mark them as managed
This commit is contained in:
Przemko Robakowski 2020-09-08 11:26:06 +02:00 committed by GitHub
parent ebd1569028
commit bb357f6aae
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
20 changed files with 2103 additions and 587 deletions

View File

@ -36,7 +36,8 @@ public class SnapshotLifecycleTemplateRegistry extends IndexTemplateRegistry {
// history (please add a comment why you increased the version here)
// version 1: initial
// version 2: converted to hidden index
public static final int INDEX_TEMPLATE_VERSION = 2;
// version 3: templates moved to composable templates
public static final int INDEX_TEMPLATE_VERSION = 3;
public static final String SLM_TEMPLATE_VERSION_VARIABLE = "xpack.slm.template.version";
public static final String SLM_TEMPLATE_NAME = ".slm-history";
@ -69,7 +70,7 @@ public class SnapshotLifecycleTemplateRegistry extends IndexTemplateRegistry {
}
@Override
protected List<IndexTemplateConfig> getLegacyTemplateConfigs() {
protected List<IndexTemplateConfig> getComposableTemplateConfigs() {
if (slmHistoryEnabled == false) {
return Collections.emptyList();
}
@ -90,9 +91,9 @@ public class SnapshotLifecycleTemplateRegistry extends IndexTemplateRegistry {
}
public boolean validate(ClusterState state) {
boolean allTemplatesPresent = getLegacyTemplateConfigs().stream()
boolean allTemplatesPresent = getComposableTemplateConfigs().stream()
.map(IndexTemplateConfig::getTemplateName)
.allMatch(name -> state.metadata().getTemplates().containsKey(name));
.allMatch(name -> state.metadata().templatesV2().containsKey(name));
Optional<Map<String, LifecyclePolicy>> maybePolicies = Optional
.<IndexLifecycleMetadata>ofNullable(state.metadata().custom(IndexLifecycleMetadata.TYPE))

View File

@ -16,15 +16,21 @@ public final class WatcherIndexTemplateRegistryField {
// version 9: add a user field defining which user executed the watch
// version 10: add support for foreach path in actions
// version 11: watch history indices are hidden
// version 12: templates changed to composable templates
// Note: if you change this, also inform the kibana team around the watcher-ui
public static final int INDEX_TEMPLATE_VERSION = 11;
public static final int INDEX_TEMPLATE_VERSION = 12;
public static final int INDEX_TEMPLATE_VERSION_10 = 10;
public static final int INDEX_TEMPLATE_VERSION_11 = 11;
public static final String HISTORY_TEMPLATE_NAME = ".watch-history-" + INDEX_TEMPLATE_VERSION;
public static final String HISTORY_TEMPLATE_NAME_10 = ".watch-history-" + INDEX_TEMPLATE_VERSION_10;
public static final String HISTORY_TEMPLATE_NAME_11 = ".watch-history-" + INDEX_TEMPLATE_VERSION_11;
public static final String HISTORY_TEMPLATE_NAME_NO_ILM = ".watch-history-no-ilm-" + INDEX_TEMPLATE_VERSION;
public static final String HISTORY_TEMPLATE_NAME_NO_ILM_10 = ".watch-history-no-ilm-10";
public static final String HISTORY_TEMPLATE_NAME_NO_ILM_11 = ".watch-history-no-ilm-" + INDEX_TEMPLATE_VERSION_11;
public static final String TRIGGERED_TEMPLATE_NAME = ".triggered_watches";
public static final String TRIGGERED_TEMPLATE_NAME_11 = ".triggered_watches-11";
public static final String WATCHES_TEMPLATE_NAME = ".watches";
public static final String WATCHES_TEMPLATE_NAME_11 = ".watches-11";
public static final String[] TEMPLATE_NAMES = new String[] {
HISTORY_TEMPLATE_NAME, TRIGGERED_TEMPLATE_NAME, WATCHES_TEMPLATE_NAME
};

View File

@ -2,7 +2,7 @@
"index_patterns": [
"ilm-history-${xpack.ilm_history.template.version}*"
],
"order": 2147483647,
"template": {
"settings": {
"index.number_of_shards": 1,
"index.number_of_replicas": 0,
@ -13,7 +13,6 @@
"index.format": 1
},
"mappings": {
"_doc": {
"dynamic": false,
"properties": {
"@timestamp": {
@ -81,5 +80,10 @@
}
}
},
"_meta": {
"description": "index template for ILM history indices",
"managed": true
},
"priority": 2147483647,
"version": ${xpack.ilm_history.template.version}
}

View File

@ -2,7 +2,8 @@
"index_patterns": [
".slm-history-${xpack.slm.template.version}*"
],
"order": 2147483647,
"priority": 2147483647,
"template": {
"settings": {
"index.number_of_shards": 1,
"index.number_of_replicas": 0,
@ -13,7 +14,6 @@
"index.format": 1
},
"mappings": {
"_doc": {
"dynamic": false,
"properties": {
"@timestamp": {
@ -57,5 +57,9 @@
}
}
},
"_meta": {
"description": "index template for SLM history indices",
"managed": true
},
"version": ${xpack.slm.template.version}
}

View File

@ -0,0 +1,41 @@
{
"index_patterns": [ ".triggered_watches*" ],
"order": 2147483647,
"settings": {
"index.number_of_shards": 1,
"index.auto_expand_replicas": "0-1",
"index.refresh_interval" : "-1",
"index.format": 6,
"index.priority": 900
},
"mappings": {
"_doc": {
"dynamic" : "strict",
"properties": {
"trigger_event": {
"type": "object",
"dynamic": true,
"enabled" : false,
"properties": {
"schedule": {
"type": "object",
"dynamic": true,
"properties": {
"triggered_time": {
"type": "date"
},
"scheduled_time": {
"type": "date"
}
}
}
}
},
"state": {
"type": "keyword"
}
}
}
},
"version": 11
}

View File

@ -1,6 +1,7 @@
{
"index_patterns": [ ".triggered_watches*" ],
"order": 2147483647,
"priority": 2147483647,
"template": {
"settings": {
"index.number_of_shards": 1,
"index.auto_expand_replicas": "0-1",
@ -9,7 +10,6 @@
"index.priority": 900
},
"mappings": {
"_doc": {
"dynamic": "strict",
"properties": {
"trigger_event": {
@ -37,5 +37,9 @@
}
}
},
"_meta": {
"description": "index template for triggered watches indices",
"managed": true
},
"version": ${xpack.watcher.template.version}
}

View File

@ -0,0 +1,568 @@
{
"index_patterns": [ ".watcher-history-11*" ],
"order": 2147483647,
"settings": {
"index.number_of_shards": 1,
"index.number_of_replicas": 0,
"index.auto_expand_replicas": "0-1",
"index.lifecycle.name": "watch-history-ilm-policy",
"index.hidden": true,
"index.format": 6
},
"mappings": {
"_doc": {
"_meta": {
"watcher-history-version": "11"
},
"dynamic_templates": [
{
"disabled_payload_fields": {
"path_match": "result\\.(input(\\..+)*|(transform(\\..+)*)|(actions\\.transform(\\..+)*))\\.payload",
"match_pattern": "regex",
"mapping": {
"type": "object",
"enabled": false
}
}
},
{
"disabled_search_request_body_fields": {
"path_match": "result\\.(input(\\..+)*|(transform(\\..+)*)|(actions\\.transform(\\..+)*))\\.search\\.request\\.(body|template)",
"match_pattern": "regex",
"mapping": {
"type": "object",
"enabled": false
}
}
},
{
"disabled_exception_fields": {
"path_match": "result\\.(input(\\..+)*|(transform(\\..+)*)|(actions\\.transform(\\..+)*)|actions)\\.error",
"match_pattern": "regex",
"mapping": {
"type": "object",
"enabled": false
}
}
},
{
"disabled_jira_custom_fields": {
"path_match": "result.actions.jira.fields.customfield_*",
"mapping": {
"type": "object",
"enabled": false
}
}
}
],
"dynamic": false,
"properties": {
"watch_id": {
"type": "keyword"
},
"node": {
"type": "keyword"
},
"trigger_event": {
"type": "object",
"dynamic": true,
"properties": {
"type" : {
"type" : "keyword"
},
"triggered_time": {
"type": "date"
},
"manual": {
"type": "object",
"dynamic": true,
"properties": {
"schedule": {
"type": "object",
"dynamic": true,
"properties": {
"scheduled_time": {
"type": "date"
}
}
}
}
},
"schedule": {
"type": "object",
"dynamic": true,
"properties": {
"scheduled_time": {
"type": "date"
}
}
}
}
},
"vars" : {
"type" : "object",
"enabled" : false
},
"input": {
"type": "object",
"enabled": false
},
"condition": {
"type": "object",
"enabled": false
},
"state": {
"type": "keyword"
},
"status": {
"type": "object",
"enabled" : false,
"dynamic" : true
},
"messages": {
"type": "text"
},
"user": {
"type": "text"
},
"exception" : {
"type" : "object",
"enabled" : false
},
"result": {
"type": "object",
"dynamic": true,
"properties": {
"execution_time": {
"type": "date"
},
"execution_duration": {
"type": "long"
},
"input": {
"type": "object",
"dynamic": true,
"properties": {
"type" : {
"type" : "keyword"
},
"status" : {
"type" : "keyword"
},
"payload" : {
"type" : "object",
"enabled" : false
},
"search": {
"type": "object",
"dynamic": true,
"properties": {
"request": {
"type": "object",
"dynamic": true,
"properties": {
"search_type": {
"type": "keyword"
},
"indices": {
"type": "keyword"
},
"types": {
"type": "keyword"
}
}
}
}
},
"http": {
"type": "object",
"dynamic": true,
"properties": {
"request": {
"type": "object",
"dynamic": true,
"properties": {
"path": {
"type": "keyword"
},
"host": {
"type": "keyword"
}
}
}
}
}
}
},
"condition" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"type" : {
"type" : "keyword"
},
"status" : {
"type" : "keyword"
},
"met" : {
"type" : "boolean"
},
"compare" : {
"type" : "object",
"enabled" : false
},
"array_compare" : {
"type" : "object",
"enabled" : false
},
"script" : {
"type" : "object",
"enabled" : false
}
}
},
"transform" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"type" : {
"type" : "keyword"
},
"search" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"request" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"indices" : {
"type" : "keyword"
},
"types" : {
"type" : "keyword"
}
}
}
}
}
}
},
"actions": {
"type": "nested",
"include_in_parent": true,
"dynamic": true,
"properties": {
"id" : {
"type" : "keyword"
},
"type" : {
"type" : "keyword"
},
"status" : {
"type" : "keyword"
},
"reason" : {
"type" : "keyword"
},
"number_of_actions_executed": {
"type": "integer"
},
"foreach" : {
"type": "object",
"enabled" : false
},
"email": {
"type": "object",
"dynamic": true,
"properties": {
"message": {
"type": "object",
"dynamic": true,
"properties": {
"id": {
"type": "keyword"
},
"from": {
"type": "keyword"
},
"reply_to": {
"type": "keyword"
},
"to": {
"type": "keyword"
},
"cc": {
"type": "keyword"
},
"bcc": {
"type": "keyword"
}
}
}
}
},
"webhook": {
"type": "object",
"dynamic": true,
"properties": {
"request": {
"type": "object",
"dynamic": true,
"properties": {
"path": {
"type": "keyword"
},
"host": {
"type": "keyword"
}
}
}
}
},
"index": {
"type": "object",
"dynamic": true,
"properties": {
"response": {
"type": "object",
"dynamic": true,
"properties": {
"index": {
"type": "keyword"
},
"type": {
"type": "keyword"
},
"id": {
"type": "keyword"
}
}
}
}
},
"jira" : {
"type": "object",
"dynamic": true,
"properties": {
"account": {
"type": "keyword"
},
"reason": {
"type": "text"
},
"request" : {
"type" : "object",
"enabled" : false
},
"response" : {
"type" : "object",
"enabled" : false
},
"fields": {
"type": "object",
"dynamic": true,
"properties": {
"summary": {
"type": "text"
},
"description": {
"type": "text"
},
"labels" : {
"type": "text"
},
"project" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"key" : {
"type" : "keyword"
},
"id" : {
"type" : "keyword"
}
}
},
"issuetype" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"name" : {
"type": "keyword"
},
"id" : {
"type" : "keyword"
}
}
}
}
},
"result": {
"type": "object",
"dynamic": true,
"properties" : {
"id" : {
"type" : "keyword"
},
"key" : {
"type" : "keyword"
},
"self" : {
"type" : "keyword"
}
}
}
}
},
"slack" : {
"type": "object",
"dynamic": true,
"properties": {
"account": {
"type": "keyword"
},
"sent_messages": {
"type": "nested",
"include_in_parent": true,
"dynamic": true,
"properties": {
"status": {
"type": "keyword"
},
"reason": {
"type": "text"
},
"request" : {
"type" : "object",
"enabled" : false
},
"response" : {
"type" : "object",
"enabled" : false
},
"to" : {
"type": "keyword"
},
"message" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"from" : {
"type" : "text"
},
"icon" : {
"type" : "keyword"
},
"text" : {
"type" : "text"
},
"attachments" : {
"type" : "nested",
"include_in_parent": true,
"dynamic" : true,
"properties" : {
"color" : {
"type" : "keyword"
},
"fields" : {
"properties" : {
"value" : {
"type" : "text"
}
}
}
}
}
}
}
}
}
}
},
"pagerduty" : {
"type": "object",
"dynamic": true,
"properties": {
"account": {
"type": "keyword"
},
"sent_event": {
"type": "nested",
"include_in_parent": true,
"dynamic": true,
"properties": {
"reason": {
"type": "text"
},
"request" : {
"type" : "object",
"enabled" : false
},
"response" : {
"type" : "object",
"enabled" : false
},
"event" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"type" : {
"type" : "keyword"
},
"client" : {
"type" : "text"
},
"client_url" : {
"type" : "keyword"
},
"account" : {
"type" : "keyword"
},
"attach_payload" : {
"type" : "boolean"
},
"incident_key" : {
"type" : "keyword"
},
"description" : {
"type" : "text"
},
"context" : {
"type" : "nested",
"include_in_parent": true,
"dynamic" : true,
"properties" : {
"type" : {
"type" : "keyword"
},
"href" : {
"type" : "keyword"
},
"src" : {
"type" : "keyword"
},
"alt" : {
"type" : "text"
}
}
}
}
}
}
}
}
}
}
}
}
},
"metadata": {
"type": "object",
"dynamic": true
}
}
}
},
"version": 11
}

View File

@ -0,0 +1,617 @@
{
"index_patterns": [ ".watcher-history-11*" ],
"order": 2147483646,
"settings": {
"index.number_of_shards": 1,
"index.number_of_replicas": 0,
"index.auto_expand_replicas": "0-1",
"index.hidden": true,
"index.format": 6
},
"mappings": {
"doc": {
"_meta": {
"watcher-history-version": "11"
},
"dynamic_templates": [
{
"disabled_payload_fields": {
"path_match": "result\\.(input(\\..+)*|(transform(\\..+)*)|(actions\\.transform(\\..+)*))\\.payload",
"match_pattern": "regex",
"mapping": {
"type": "object",
"enabled": false
}
}
},
{
"disabled_search_request_body_fields": {
"path_match": "result\\.(input(\\..+)*|(transform(\\..+)*)|(actions\\.transform(\\..+)*))\\.search\\.request\\.(body|template)",
"match_pattern": "regex",
"mapping": {
"type": "object",
"enabled": false
}
}
},
{
"disabled_exception_fields": {
"path_match": "result\\.(input(\\..+)*|(transform(\\..+)*)|(actions\\.transform(\\..+)*)|actions)\\.error",
"match_pattern": "regex",
"mapping": {
"type": "object",
"enabled": false
}
}
},
{
"disabled_jira_custom_fields": {
"path_match": "result.actions.jira.fields.customfield_*",
"mapping": {
"type": "object",
"enabled": false
}
}
}
],
"dynamic": false,
"properties": {
"watch_id": {
"type": "keyword"
},
"node": {
"type": "keyword"
},
"trigger_event": {
"type": "object",
"dynamic": true,
"properties": {
"type" : {
"type" : "keyword"
},
"triggered_time": {
"type": "date"
},
"manual": {
"type": "object",
"dynamic": true,
"properties": {
"schedule": {
"type": "object",
"dynamic": true,
"properties": {
"scheduled_time": {
"type": "date"
}
}
}
}
},
"schedule": {
"type": "object",
"dynamic": true,
"properties": {
"scheduled_time": {
"type": "date"
}
}
}
}
},
"vars" : {
"type" : "object",
"enabled" : false
},
"input": {
"type": "object",
"enabled": false
},
"condition": {
"type": "object",
"enabled": false
},
"state": {
"type": "keyword"
},
"status": {
"type": "object",
"enabled" : false,
"dynamic" : true
},
"messages": {
"type": "text"
},
"user": {
"type": "text"
},
"exception" : {
"type" : "object",
"enabled" : false
},
"result": {
"type": "object",
"dynamic": true,
"properties": {
"execution_time": {
"type": "date"
},
"execution_duration": {
"type": "long"
},
"input": {
"type": "object",
"dynamic": true,
"properties": {
"type" : {
"type" : "keyword"
},
"status" : {
"type" : "keyword"
},
"payload" : {
"type" : "object",
"enabled" : false
},
"search": {
"type": "object",
"dynamic": true,
"properties": {
"request": {
"type": "object",
"dynamic": true,
"properties": {
"search_type": {
"type": "keyword"
},
"indices": {
"type": "keyword"
},
"types": {
"type": "keyword"
}
}
}
}
},
"http": {
"type": "object",
"dynamic": true,
"properties": {
"request": {
"type": "object",
"dynamic": true,
"properties": {
"path": {
"type": "keyword"
},
"host": {
"type": "keyword"
}
}
}
}
}
}
},
"condition" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"type" : {
"type" : "keyword"
},
"status" : {
"type" : "keyword"
},
"met" : {
"type" : "boolean"
},
"compare" : {
"type" : "object",
"enabled" : false
},
"array_compare" : {
"type" : "object",
"enabled" : false
},
"script" : {
"type" : "object",
"enabled" : false
}
}
},
"transform" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"type" : {
"type" : "keyword"
},
"search" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"request" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"indices" : {
"type" : "keyword"
},
"types" : {
"type" : "keyword"
}
}
}
}
}
}
},
"actions": {
"type": "nested",
"include_in_parent": true,
"dynamic": true,
"properties": {
"id" : {
"type" : "keyword"
},
"type" : {
"type" : "keyword"
},
"status" : {
"type" : "keyword"
},
"reason" : {
"type" : "keyword"
},
"email": {
"type": "object",
"dynamic": true,
"properties": {
"message": {
"type": "object",
"dynamic": true,
"properties": {
"id": {
"type": "keyword"
},
"from": {
"type": "keyword"
},
"reply_to": {
"type": "keyword"
},
"to": {
"type": "keyword"
},
"cc": {
"type": "keyword"
},
"bcc": {
"type": "keyword"
}
}
}
}
},
"webhook": {
"type": "object",
"dynamic": true,
"properties": {
"request": {
"type": "object",
"dynamic": true,
"properties": {
"path": {
"type": "keyword"
},
"host": {
"type": "keyword"
}
}
}
}
},
"index": {
"type": "object",
"dynamic": true,
"properties": {
"response": {
"type": "object",
"dynamic": true,
"properties": {
"index": {
"type": "keyword"
},
"type": {
"type": "keyword"
},
"id": {
"type": "keyword"
}
}
}
}
},
"hipchat" : {
"type": "object",
"dynamic": true,
"properties": {
"account": {
"type": "keyword"
},
"sent_messages": {
"type": "nested",
"include_in_parent": true,
"dynamic": true,
"properties": {
"status": {
"type": "keyword"
},
"reason": {
"type": "text"
},
"request" : {
"type" : "object",
"enabled" : false
},
"response" : {
"type" : "object",
"enabled" : false
},
"room" : {
"type": "keyword"
},
"user" : {
"type": "keyword"
},
"message" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"message_format" : {
"type" : "keyword"
},
"color" : {
"type" : "keyword"
},
"notify" : {
"type" : "boolean"
},
"message" : {
"type" : "text"
},
"from" : {
"type" : "text"
}
}
}
}
}
}
},
"jira" : {
"type": "object",
"dynamic": true,
"properties": {
"account": {
"type": "keyword"
},
"reason": {
"type": "text"
},
"request" : {
"type" : "object",
"enabled" : false
},
"response" : {
"type" : "object",
"enabled" : false
},
"fields": {
"type": "object",
"dynamic": true,
"properties": {
"summary": {
"type": "text"
},
"description": {
"type": "text"
},
"labels" : {
"type": "text"
},
"project" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"key" : {
"type" : "keyword"
},
"id" : {
"type" : "keyword"
}
}
},
"issuetype" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"name" : {
"type": "keyword"
},
"id" : {
"type" : "keyword"
}
}
}
}
},
"result": {
"type": "object",
"dynamic": true,
"properties" : {
"id" : {
"type" : "keyword"
},
"key" : {
"type" : "keyword"
},
"self" : {
"type" : "keyword"
}
}
}
}
},
"slack" : {
"type": "object",
"dynamic": true,
"properties": {
"account": {
"type": "keyword"
},
"sent_messages": {
"type": "nested",
"include_in_parent": true,
"dynamic": true,
"properties": {
"status": {
"type": "keyword"
},
"reason": {
"type": "text"
},
"request" : {
"type" : "object",
"enabled" : false
},
"response" : {
"type" : "object",
"enabled" : false
},
"to" : {
"type": "keyword"
},
"message" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"from" : {
"type" : "text"
},
"icon" : {
"type" : "keyword"
},
"text" : {
"type" : "text"
},
"attachments" : {
"type" : "nested",
"include_in_parent": true,
"dynamic" : true,
"properties" : {
"color" : {
"type" : "keyword"
},
"fields" : {
"properties" : {
"value" : {
"type" : "text"
}
}
}
}
}
}
}
}
}
}
},
"pagerduty" : {
"type": "object",
"dynamic": true,
"properties": {
"account": {
"type": "keyword"
},
"sent_event": {
"type": "nested",
"include_in_parent": true,
"dynamic": true,
"properties": {
"reason": {
"type": "text"
},
"request" : {
"type" : "object",
"enabled" : false
},
"response" : {
"type" : "object",
"enabled" : false
},
"event" : {
"type" : "object",
"dynamic" : true,
"properties" : {
"type" : {
"type" : "keyword"
},
"client" : {
"type" : "text"
},
"client_url" : {
"type" : "keyword"
},
"account" : {
"type" : "keyword"
},
"attach_payload" : {
"type" : "boolean"
},
"incident_key" : {
"type" : "keyword"
},
"description" : {
"type" : "text"
},
"context" : {
"type" : "nested",
"include_in_parent": true,
"dynamic" : true,
"properties" : {
"type" : {
"type" : "keyword"
},
"href" : {
"type" : "keyword"
},
"src" : {
"type" : "keyword"
},
"alt" : {
"type" : "text"
}
}
}
}
}
}
}
}
}
}
}
}
},
"metadata": {
"type": "object",
"dynamic": true
}
}
}
},
"version": 11
}

View File

@ -1,6 +1,7 @@
{
"index_patterns": [ ".watcher-history-${xpack.watcher.template.version}*" ],
"order": 2147483646,
"priority": 2147483646,
"template": {
"settings": {
"index.number_of_shards": 1,
"index.number_of_replicas": 0,
@ -9,7 +10,6 @@
"index.format": 6
},
"mappings": {
"doc": {
"_meta": {
"watcher-history-version": "${xpack.watcher.template.version}"
},
@ -613,5 +613,9 @@
}
}
},
"_meta": {
"description": "index template for watcher history indices",
"managed": true
},
"version": ${xpack.watcher.template.version}
}

View File

@ -1,6 +1,7 @@
{
"index_patterns": [ ".watcher-history-${xpack.watcher.template.version}*" ],
"order": 2147483647,
"priority": 2147483647,
"template": {
"settings": {
"index.number_of_shards": 1,
"index.number_of_replicas": 0,
@ -10,7 +11,6 @@
"index.format": 6
},
"mappings": {
"_doc": {
"_meta": {
"watcher-history-version": "${xpack.watcher.template.version}"
},
@ -564,5 +564,9 @@
}
}
},
"_meta": {
"description": "index template for watcher history indices",
"managed": true
},
"version": ${xpack.watcher.template.version}
}

View File

@ -0,0 +1,63 @@
{
"index_patterns": [ ".watches*" ],
"order": 2147483647,
"settings": {
"index.number_of_shards": 1,
"index.number_of_replicas": 0,
"index.auto_expand_replicas": "0-1",
"index.format": 6,
"index.priority": 800
},
"mappings": {
"_doc": {
"dynamic" : "strict",
"properties": {
"status": {
"type": "object",
"enabled" : false,
"dynamic" : true
},
"trigger" : {
"type": "object",
"enabled" : false,
"dynamic" : true
},
"input": {
"type": "object",
"enabled" : false,
"dynamic" : true
},
"condition": {
"type": "object",
"enabled" : false,
"dynamic" : true
},
"throttle_period": {
"type" : "keyword",
"index" : false,
"doc_values" : false
},
"throttle_period_in_millis": {
"type" : "long",
"index" : false,
"doc_values" : false
},
"transform": {
"type" : "object",
"enabled" : false,
"dynamic" : true
},
"actions": {
"type" : "object",
"enabled" : false,
"dynamic" : true
},
"metadata" : {
"type" : "object",
"dynamic": true
}
}
}
},
"version": 11
}

View File

@ -1,6 +1,7 @@
{
"index_patterns": [ ".watches*" ],
"order": 2147483647,
"priority": 2147483647,
"template": {
"settings": {
"index.number_of_shards": 1,
"index.number_of_replicas": 0,
@ -9,7 +10,6 @@
"index.priority": 800
},
"mappings": {
"_doc": {
"dynamic": "strict",
"properties": {
"status": {
@ -59,5 +59,9 @@
}
}
},
"_meta": {
"description": "index template for watches indices",
"managed": true
},
"version": ${xpack.watcher.template.version}
}

View File

@ -11,22 +11,20 @@ import org.elasticsearch.action.ActionListener;
import org.elasticsearch.action.ActionRequest;
import org.elasticsearch.action.ActionResponse;
import org.elasticsearch.action.ActionType;
import org.elasticsearch.action.admin.indices.template.put.PutIndexTemplateAction;
import org.elasticsearch.action.admin.indices.template.put.PutIndexTemplateRequest;
import org.elasticsearch.action.admin.indices.template.put.PutComposableIndexTemplateAction;
import org.elasticsearch.action.support.master.AcknowledgedResponse;
import org.elasticsearch.cluster.ClusterChangedEvent;
import org.elasticsearch.cluster.ClusterModule;
import org.elasticsearch.cluster.ClusterName;
import org.elasticsearch.cluster.ClusterState;
import org.elasticsearch.cluster.block.ClusterBlocks;
import org.elasticsearch.cluster.metadata.IndexTemplateMetadata;
import org.elasticsearch.cluster.metadata.ComposableIndexTemplate;
import org.elasticsearch.cluster.metadata.Metadata;
import org.elasticsearch.cluster.node.DiscoveryNode;
import org.elasticsearch.cluster.node.DiscoveryNodes;
import org.elasticsearch.cluster.service.ClusterService;
import org.elasticsearch.common.ParseField;
import org.elasticsearch.common.TriFunction;
import org.elasticsearch.common.collect.ImmutableOpenMap;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.xcontent.LoggingDeprecationHandler;
import org.elasticsearch.common.xcontent.NamedXContentRegistry;
@ -105,7 +103,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
Settings settings = Settings.builder().put(SLM_HISTORY_INDEX_ENABLED_SETTING.getKey(), false).build();
SnapshotLifecycleTemplateRegistry disabledRegistry = new SnapshotLifecycleTemplateRegistry(settings, clusterService, threadPool,
client, xContentRegistry);
assertThat(disabledRegistry.getLegacyTemplateConfigs(), hasSize(0));
assertThat(disabledRegistry.getComposableTemplateConfigs(), hasSize(0));
assertThat(disabledRegistry.getPolicyConfigs(), hasSize(0));
}
@ -119,7 +117,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
AtomicInteger calledTimes = new AtomicInteger(0);
client.setVerifier((action, request, listener) -> verifyTemplateInstalled(calledTimes, action, request, listener));
registry.clusterChanged(event);
assertBusy(() -> assertThat(calledTimes.get(), equalTo(registry.getLegacyTemplateConfigs().size())));
assertBusy(() -> assertThat(calledTimes.get(), equalTo(registry.getComposableTemplateConfigs().size())));
calledTimes.set(0);
@ -149,7 +147,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
assertThat(putRequest.getPolicy().getName(), equalTo(SLM_POLICY_NAME));
assertNotNull(listener);
return new PutLifecycleAction.Response(true);
} else if (action instanceof PutIndexTemplateAction) {
} else if (action instanceof PutComposableIndexTemplateAction) {
// Ignore this, it's verified in another test
return new TestPutIndexTemplateResponse(true);
} else {
@ -176,7 +174,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
policyMap.put(policy.getName(), policy);
client.setVerifier((action, request, listener) -> {
if (action instanceof PutIndexTemplateAction) {
if (action instanceof PutComposableIndexTemplateAction) {
// Ignore this, it's verified in another test
return new TestPutIndexTemplateResponse(true);
} else if (action instanceof PutLifecycleAction) {
@ -204,7 +202,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
LifecyclePolicy policy = policies.get(0);
client.setVerifier((action, request, listener) -> {
if (action instanceof PutIndexTemplateAction) {
if (action instanceof PutComposableIndexTemplateAction) {
// Ignore this, it's verified in another test
return new TestPutIndexTemplateResponse(true);
} else if (action instanceof PutLifecycleAction) {
@ -233,7 +231,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
AtomicInteger calledTimes = new AtomicInteger(0);
client.setVerifier((action, request, listener) -> verifyTemplateInstalled(calledTimes, action, request, listener));
registry.clusterChanged(event);
assertBusy(() -> assertThat(calledTimes.get(), equalTo(registry.getLegacyTemplateConfigs().size())));
assertBusy(() -> assertThat(calledTimes.get(), equalTo(registry.getComposableTemplateConfigs().size())));
}
public void testThatUnversionedOldTemplatesAreUpgraded() throws Exception {
@ -244,7 +242,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
AtomicInteger calledTimes = new AtomicInteger(0);
client.setVerifier((action, request, listener) -> verifyTemplateInstalled(calledTimes, action, request, listener));
registry.clusterChanged(event);
assertBusy(() -> assertThat(calledTimes.get(), equalTo(registry.getLegacyTemplateConfigs().size())));
assertBusy(() -> assertThat(calledTimes.get(), equalTo(registry.getComposableTemplateConfigs().size())));
}
@ -256,7 +254,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
Collections.singletonMap(SLM_TEMPLATE_NAME, INDEX_TEMPLATE_VERSION), nodes);
AtomicInteger calledTimes = new AtomicInteger(0);
client.setVerifier((action, request, listener) -> {
if (action instanceof PutIndexTemplateAction) {
if (action instanceof PutComposableIndexTemplateAction) {
fail("template should not have been re-installed");
return null;
} else if (action instanceof PutLifecycleAction) {
@ -340,14 +338,14 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
private ActionResponse verifyTemplateInstalled(
AtomicInteger calledTimes, ActionType<?> action, ActionRequest request, ActionListener<?> listener) {
if (action instanceof PutIndexTemplateAction) {
if (action instanceof PutComposableIndexTemplateAction) {
calledTimes.incrementAndGet();
assertThat(action, instanceOf(PutIndexTemplateAction.class));
assertThat(request, instanceOf(PutIndexTemplateRequest.class));
final PutIndexTemplateRequest putRequest = (PutIndexTemplateRequest) request;
assertThat(action, instanceOf(PutComposableIndexTemplateAction.class));
assertThat(request, instanceOf(PutComposableIndexTemplateAction.Request.class));
final PutComposableIndexTemplateAction.Request putRequest = (PutComposableIndexTemplateAction.Request) request;
assertThat(putRequest.name(), equalTo(SLM_TEMPLATE_NAME));
assertThat(putRequest.settings().get("index.lifecycle.name"), equalTo(SLM_POLICY_NAME));
assertThat(putRequest.version(), equalTo(INDEX_TEMPLATE_VERSION));
assertThat(putRequest.indexTemplate().template().settings().get("index.lifecycle.name"), equalTo(SLM_POLICY_NAME));
assertThat(putRequest.indexTemplate().version(), equalTo((long) INDEX_TEMPLATE_VERSION));
assertNotNull(listener);
return new TestPutIndexTemplateResponse(true);
} else if (action instanceof PutLifecycleAction) {
@ -377,11 +375,11 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
private ClusterState createClusterState(Settings nodeSettings, Map<String, Integer> existingTemplates,
Map<String, LifecyclePolicy> existingPolicies, DiscoveryNodes nodes) {
ImmutableOpenMap.Builder<String, IndexTemplateMetadata> indexTemplates = ImmutableOpenMap.builder();
Map<String, ComposableIndexTemplate> indexTemplates = new HashMap<>();
for (Map.Entry<String, Integer> template : existingTemplates.entrySet()) {
final IndexTemplateMetadata mockTemplate = mock(IndexTemplateMetadata.class);
when(mockTemplate.version()).thenReturn(template.getValue());
when(mockTemplate.getVersion()).thenReturn(template.getValue());
final ComposableIndexTemplate mockTemplate = mock(ComposableIndexTemplate.class);
Long version = template.getValue() == null ? null : (long) template.getValue();
when(mockTemplate.version()).thenReturn(version);
indexTemplates.put(template.getKey(), mockTemplate);
}
@ -392,7 +390,7 @@ public class SnapshotLifecycleTemplateRegistryTests extends ESTestCase {
return ClusterState.builder(new ClusterName("test"))
.metadata(Metadata.builder()
.templates(indexTemplates.build())
.indexTemplates(indexTemplates)
.transientSettings(nodeSettings)
.putCustom(IndexLifecycleMetadata.TYPE, ilmMeta)
.build())

View File

@ -0,0 +1,135 @@
/*
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
* or more contributor license agreements. Licensed under the Elastic License;
* you may not use this file except in compliance with the Elastic License.
*/
package org.elasticsearch.xpack.ilm;
import org.elasticsearch.action.admin.indices.create.CreateIndexResponse;
import org.elasticsearch.action.admin.indices.get.GetIndexResponse;
import org.elasticsearch.action.admin.indices.rollover.RolloverResponse;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.unit.TimeValue;
import org.elasticsearch.plugins.Plugin;
import org.elasticsearch.test.ESIntegTestCase;
import org.elasticsearch.xpack.core.LocalStateCompositeXPackPlugin;
import org.elasticsearch.xpack.core.XPackSettings;
import org.elasticsearch.xpack.core.ilm.LifecyclePolicy;
import org.elasticsearch.xpack.core.ilm.LifecycleSettings;
import org.elasticsearch.xpack.core.ilm.OperationMode;
import org.elasticsearch.xpack.core.ilm.Phase;
import org.elasticsearch.xpack.core.ilm.StopILMRequest;
import org.elasticsearch.xpack.core.ilm.action.GetStatusAction;
import org.elasticsearch.xpack.core.ilm.action.PutLifecycleAction;
import org.elasticsearch.xpack.core.ilm.action.StopILMAction;
import org.elasticsearch.xpack.ilm.history.ILMHistoryStore;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import static org.elasticsearch.cluster.metadata.IndexMetadata.SETTING_NUMBER_OF_REPLICAS;
import static org.elasticsearch.cluster.metadata.IndexMetadata.SETTING_NUMBER_OF_SHARDS;
import static org.elasticsearch.index.query.QueryBuilders.matchQuery;
import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertAcked;
import static org.elasticsearch.test.hamcrest.ElasticsearchAssertions.assertHitCount;
import static org.hamcrest.Matchers.arrayContaining;
import static org.hamcrest.Matchers.is;
@ESIntegTestCase.ClusterScope(scope = ESIntegTestCase.Scope.TEST, numDataNodes = 0)
public class ILMHistoryTests extends ESIntegTestCase {
@Override
protected Settings nodeSettings(int nodeOrdinal) {
Settings.Builder settings = Settings.builder().put(super.nodeSettings(nodeOrdinal));
settings.put(XPackSettings.MACHINE_LEARNING_ENABLED.getKey(), false);
settings.put(XPackSettings.SECURITY_ENABLED.getKey(), false);
settings.put(XPackSettings.WATCHER_ENABLED.getKey(), false);
settings.put(XPackSettings.GRAPH_ENABLED.getKey(), false);
settings.put(LifecycleSettings.LIFECYCLE_POLL_INTERVAL, "1s");
settings.put(LifecycleSettings.SLM_HISTORY_INDEX_ENABLED_SETTING.getKey(), false);
return settings.build();
}
@Override
protected boolean ignoreExternalCluster() {
return true;
}
@Override
protected Collection<Class<? extends Plugin>> nodePlugins() {
return Arrays.asList(LocalStateCompositeXPackPlugin.class, IndexLifecycle.class);
}
@Override
protected Settings transportClientSettings() {
Settings.Builder settings = Settings.builder().put(super.transportClientSettings());
settings.put(XPackSettings.MACHINE_LEARNING_ENABLED.getKey(), false);
settings.put(XPackSettings.SECURITY_ENABLED.getKey(), false);
settings.put(XPackSettings.WATCHER_ENABLED.getKey(), false);
settings.put(XPackSettings.GRAPH_ENABLED.getKey(), false);
return settings.build();
}
@Override
protected Collection<Class<? extends Plugin>> transportClientPlugins() {
return nodePlugins();
}
private void putTestPolicy() throws InterruptedException, java.util.concurrent.ExecutionException {
Phase phase = new Phase("hot", TimeValue.ZERO, Collections.emptyMap());
LifecyclePolicy lifecyclePolicy = new LifecyclePolicy("test", Collections.singletonMap("hot", phase));
PutLifecycleAction.Request putLifecycleRequest = new PutLifecycleAction.Request(lifecyclePolicy);
PutLifecycleAction.Response putLifecycleResponse = client().execute(PutLifecycleAction.INSTANCE, putLifecycleRequest).get();
assertAcked(putLifecycleResponse);
}
public void testIlmHistoryIndexCanRollover() throws Exception {
putTestPolicy();
Settings settings = Settings.builder().put(indexSettings()).put(SETTING_NUMBER_OF_SHARDS, 1)
.put(SETTING_NUMBER_OF_REPLICAS, 0).put(LifecycleSettings.LIFECYCLE_NAME, "test").build();
CreateIndexResponse res = client().admin().indices().prepareCreate("test").setSettings(settings).get();
assertTrue(res.isAcknowledged());
String firstIndex = ILMHistoryStore.ILM_HISTORY_INDEX_PREFIX + "000001";
String secondIndex = ILMHistoryStore.ILM_HISTORY_INDEX_PREFIX + "000002";
assertBusy(() -> {
try {
GetIndexResponse getIndexResponse = client().admin().indices().prepareGetIndex().setIndices(firstIndex).get();
assertThat(getIndexResponse.getIndices(), arrayContaining(firstIndex));
} catch (Exception e) {
fail(e.getMessage());
}
});
//wait for all history items to index to avoid waiting for timeout in ILMHistoryStore beforeBulk
assertBusy(() -> {
try {
SearchResponse search = client().prepareSearch(firstIndex).setQuery(matchQuery("index", firstIndex)).setSize(0).get();
assertHitCount(search, 9);
} catch (Exception e) {
//assertBusy will stop on first non-assertion error and it can happen when we try to search too early
//instead of failing the whole test change it to assertion error and wait some more time
fail(e.getMessage());
}
});
//make sure ILM is stopped so no new items will be queued in ILM history
assertTrue(client().execute(StopILMAction.INSTANCE, new StopILMRequest()).actionGet().isAcknowledged());
assertBusy(() -> {
GetStatusAction.Response status = client().execute(GetStatusAction.INSTANCE, new GetStatusAction.Request()).actionGet();
assertThat(status.getMode(), is(OperationMode.STOPPED));
});
RolloverResponse rolloverResponse = client().admin().indices().prepareRolloverIndex(ILMHistoryStore.ILM_HISTORY_ALIAS).get();
assertTrue(rolloverResponse.isAcknowledged());
assertThat(rolloverResponse.getNewIndex(), is(secondIndex));
GetIndexResponse getIndexResponse = client().admin().indices().prepareGetIndex().setIndices(secondIndex).get();
assertThat(getIndexResponse.getIndices(), arrayContaining(secondIndex));
}
}

View File

@ -182,6 +182,8 @@ public class ILMHistoryStore implements Closeable {
byte[] templateBytes = TEMPLATE_ILM_HISTORY.loadBytes();
Map<String, Object> templateAsMap = XContentHelper.convertToMap(new BytesArray(templateBytes, 0, templateBytes.length),
false, XContentType.JSON).v2();
templateAsMap = (Map<String, Object>) templateAsMap.get("template");
client.admin().indices().prepareCreate(initialHistoryIndexName)
.setSettings((Map<String, ?>) templateAsMap.get("settings"))

View File

@ -28,7 +28,8 @@ public class ILMHistoryTemplateRegistry extends IndexTemplateRegistry {
// history (please add a comment why you increased the version here)
// version 1: initial
// version 2: convert to hidden index
public static final int INDEX_TEMPLATE_VERSION = 2;
// version 3: templates moved to composable templates
public static final int INDEX_TEMPLATE_VERSION = 3;
public static final String ILM_TEMPLATE_VERSION_VARIABLE = "xpack.ilm_history.template.version";
public static final String ILM_TEMPLATE_NAME = "ilm-history";
@ -62,7 +63,7 @@ public class ILMHistoryTemplateRegistry extends IndexTemplateRegistry {
}
@Override
protected List<IndexTemplateConfig> getLegacyTemplateConfigs() {
protected List<IndexTemplateConfig> getComposableTemplateConfigs() {
if (this.ilmHistoryEnabled) {
return Collections.singletonList(TEMPLATE_ILM_HISTORY);
} else {

View File

@ -11,7 +11,7 @@ import org.elasticsearch.action.admin.indices.alias.Alias;
import org.elasticsearch.action.admin.indices.alias.get.GetAliasesResponse;
import org.elasticsearch.action.admin.indices.create.CreateIndexResponse;
import org.elasticsearch.action.admin.indices.get.GetIndexResponse;
import org.elasticsearch.action.admin.indices.template.get.GetIndexTemplatesResponse;
import org.elasticsearch.action.admin.indices.template.get.GetComposableIndexTemplateAction;
import org.elasticsearch.action.search.SearchRequestBuilder;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.action.support.IndicesOptions;
@ -486,12 +486,15 @@ public abstract class AbstractWatcherIntegrationTestCase extends ESIntegTestCase
private void ensureWatcherTemplatesAdded() throws Exception {
// Verify that the index templates exist:
assertBusy(() -> {
GetIndexTemplatesResponse response = client().admin().indices().prepareGetTemplates(HISTORY_TEMPLATE_NAME).get();
assertThat("[" + HISTORY_TEMPLATE_NAME + "] is missing", response.getIndexTemplates().size(), equalTo(1));
response = client().admin().indices().prepareGetTemplates(TRIGGERED_TEMPLATE_NAME).get();
assertThat("[" + TRIGGERED_TEMPLATE_NAME + "] is missing", response.getIndexTemplates().size(), equalTo(1));
response = client().admin().indices().prepareGetTemplates(WATCHES_TEMPLATE_NAME).get();
assertThat("[" + WATCHES_TEMPLATE_NAME + "] is missing", response.getIndexTemplates().size(), equalTo(1));
GetComposableIndexTemplateAction.Response response = client().execute(GetComposableIndexTemplateAction.INSTANCE,
new GetComposableIndexTemplateAction.Request(HISTORY_TEMPLATE_NAME)).get();
assertThat("[" + HISTORY_TEMPLATE_NAME + "] is missing", response.indexTemplates().size(), equalTo(1));
response = client().execute(GetComposableIndexTemplateAction.INSTANCE,
new GetComposableIndexTemplateAction.Request(TRIGGERED_TEMPLATE_NAME)).get();
assertThat("[" + TRIGGERED_TEMPLATE_NAME + "] is missing", response.indexTemplates().size(), equalTo(1));
response = client().execute(GetComposableIndexTemplateAction.INSTANCE,
new GetComposableIndexTemplateAction.Request(WATCHES_TEMPLATE_NAME)).get();
assertThat("[" + WATCHES_TEMPLATE_NAME + "] is missing", response.indexTemplates().size(), equalTo(1));
});
}

View File

@ -32,6 +32,11 @@ public class WatcherIndexTemplateRegistry extends IndexTemplateRegistry {
"/triggered-watches.json",
WatcherIndexTemplateRegistryField.INDEX_TEMPLATE_VERSION,
WATCHER_TEMPLATE_VERSION_VARIABLE);
public static final IndexTemplateConfig TEMPLATE_CONFIG_TRIGGERED_WATCHES_11 = new IndexTemplateConfig(
WatcherIndexTemplateRegistryField.TRIGGERED_TEMPLATE_NAME_11,
"/triggered-watches-11.json",
11,
WATCHER_TEMPLATE_VERSION_VARIABLE);
public static final IndexTemplateConfig TEMPLATE_CONFIG_WATCH_HISTORY = new IndexTemplateConfig(
WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME,
"/watch-history.json",
@ -42,6 +47,11 @@ public class WatcherIndexTemplateRegistry extends IndexTemplateRegistry {
"/watch-history-10.json",
10,
WATCHER_TEMPLATE_VERSION_VARIABLE);
public static final IndexTemplateConfig TEMPLATE_CONFIG_WATCH_HISTORY_11 = new IndexTemplateConfig(
WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_11,
"/watch-history-11.json",
11,
WATCHER_TEMPLATE_VERSION_VARIABLE);
public static final IndexTemplateConfig TEMPLATE_CONFIG_WATCH_HISTORY_NO_ILM = new IndexTemplateConfig(
WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_NO_ILM,
"/watch-history-no-ilm.json",
@ -52,11 +62,21 @@ public class WatcherIndexTemplateRegistry extends IndexTemplateRegistry {
"/watch-history-no-ilm-10.json",
10,
WATCHER_TEMPLATE_VERSION_VARIABLE);
public static final IndexTemplateConfig TEMPLATE_CONFIG_WATCH_HISTORY_NO_ILM_11 = new IndexTemplateConfig(
WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_NO_ILM_11,
"/watch-history-no-ilm-11.json",
11,
WATCHER_TEMPLATE_VERSION_VARIABLE);
public static final IndexTemplateConfig TEMPLATE_CONFIG_WATCHES = new IndexTemplateConfig(
WatcherIndexTemplateRegistryField.WATCHES_TEMPLATE_NAME,
"/watches.json",
WatcherIndexTemplateRegistryField.INDEX_TEMPLATE_VERSION,
WATCHER_TEMPLATE_VERSION_VARIABLE);
public static final IndexTemplateConfig TEMPLATE_CONFIG_WATCHES_11 = new IndexTemplateConfig(
WatcherIndexTemplateRegistryField.WATCHES_TEMPLATE_NAME_11,
"/watches-11.json",
11,
WATCHER_TEMPLATE_VERSION_VARIABLE);
public static final LifecyclePolicyConfig POLICY_WATCH_HISTORY = new LifecyclePolicyConfig("watch-history-ilm-policy",
"/watch-history-ilm-policy.json");
@ -71,19 +91,30 @@ public class WatcherIndexTemplateRegistry extends IndexTemplateRegistry {
@Override
protected List<IndexTemplateConfig> getLegacyTemplateConfigs() {
if (clusterService.state().nodes().getMinNodeVersion().onOrAfter(Version.V_7_7_0)) {
if (clusterService.state().nodes().getMinNodeVersion().onOrAfter(Version.V_7_9_0)) {
return Collections.emptyList();
} else if (clusterService.state().nodes().getMinNodeVersion().onOrAfter(Version.V_7_7_0)) {
return Arrays.asList(
ilmManagementEnabled ? TEMPLATE_CONFIG_WATCH_HISTORY_11 : TEMPLATE_CONFIG_WATCH_HISTORY_NO_ILM_11,
TEMPLATE_CONFIG_TRIGGERED_WATCHES_11,
TEMPLATE_CONFIG_WATCHES_11
);
} else {
return Arrays.asList(
ilmManagementEnabled ? TEMPLATE_CONFIG_WATCH_HISTORY_10 : TEMPLATE_CONFIG_WATCH_HISTORY_NO_ILM_10,
TEMPLATE_CONFIG_TRIGGERED_WATCHES_11,
TEMPLATE_CONFIG_WATCHES_11
);
}
}
@Override
protected List<IndexTemplateConfig> getComposableTemplateConfigs() {
return Arrays.asList(
ilmManagementEnabled ? TEMPLATE_CONFIG_WATCH_HISTORY : TEMPLATE_CONFIG_WATCH_HISTORY_NO_ILM,
TEMPLATE_CONFIG_TRIGGERED_WATCHES,
TEMPLATE_CONFIG_WATCHES
);
} else {
return Arrays.asList(
ilmManagementEnabled ? TEMPLATE_CONFIG_WATCH_HISTORY_10 : TEMPLATE_CONFIG_WATCH_HISTORY_NO_ILM_10,
TEMPLATE_CONFIG_TRIGGERED_WATCHES,
TEMPLATE_CONFIG_WATCHES
);
}
}
/**
@ -103,16 +134,21 @@ public class WatcherIndexTemplateRegistry extends IndexTemplateRegistry {
}
public static boolean validate(ClusterState state) {
if (state.nodes().getMinNodeVersion().onOrAfter(Version.V_7_7_0)) {
return (state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME) ||
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_NO_ILM)) &&
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.TRIGGERED_TEMPLATE_NAME) &&
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.WATCHES_TEMPLATE_NAME);
if(state.nodes().getMinNodeVersion().onOrAfter(Version.V_7_9_0)){
return (state.getMetadata().templatesV2().containsKey(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME) ||
state.getMetadata().templatesV2().containsKey(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_NO_ILM)) &&
state.getMetadata().templatesV2().containsKey(WatcherIndexTemplateRegistryField.TRIGGERED_TEMPLATE_NAME) &&
state.getMetadata().templatesV2().containsKey(WatcherIndexTemplateRegistryField.WATCHES_TEMPLATE_NAME);
} else if (state.nodes().getMinNodeVersion().onOrAfter(Version.V_7_7_0)) {
return (state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_11) ||
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_NO_ILM_11)) &&
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.TRIGGERED_TEMPLATE_NAME_11) &&
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.WATCHES_TEMPLATE_NAME_11);
} else {
return (state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_10) ||
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_NO_ILM_10)) &&
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.TRIGGERED_TEMPLATE_NAME) &&
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.WATCHES_TEMPLATE_NAME);
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.TRIGGERED_TEMPLATE_NAME_11) &&
state.getMetadata().getTemplates().containsKey(WatcherIndexTemplateRegistryField.WATCHES_TEMPLATE_NAME_11);
}
}

View File

@ -7,6 +7,7 @@ package org.elasticsearch.xpack.watcher.support;
import org.elasticsearch.Version;
import org.elasticsearch.action.ActionListener;
import org.elasticsearch.action.admin.indices.template.put.PutComposableIndexTemplateAction;
import org.elasticsearch.action.admin.indices.template.put.PutIndexTemplateRequest;
import org.elasticsearch.action.support.master.AcknowledgedResponse;
import org.elasticsearch.client.AdminClient;
@ -17,6 +18,7 @@ import org.elasticsearch.cluster.ClusterModule;
import org.elasticsearch.cluster.ClusterName;
import org.elasticsearch.cluster.ClusterState;
import org.elasticsearch.cluster.block.ClusterBlocks;
import org.elasticsearch.cluster.metadata.ComposableIndexTemplate;
import org.elasticsearch.cluster.metadata.IndexTemplateMetadata;
import org.elasticsearch.cluster.metadata.Metadata;
import org.elasticsearch.cluster.node.DiscoveryNode;
@ -54,6 +56,7 @@ import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;
import static org.elasticsearch.mock.orig.Mockito.verify;
@ -65,6 +68,8 @@ import static org.hamcrest.Matchers.is;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.anyObject;
import static org.mockito.Matchers.eq;
import static org.mockito.Matchers.same;
import static org.mockito.Mockito.atLeastOnce;
import static org.mockito.Mockito.doAnswer;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.spy;
@ -114,8 +119,9 @@ public class WatcherIndexTemplateRegistryTests extends ESTestCase {
ClusterChangedEvent event = createClusterChangedEvent(Collections.emptyMap(), nodes);
registry.clusterChanged(event);
ArgumentCaptor<PutIndexTemplateRequest> argumentCaptor = ArgumentCaptor.forClass(PutIndexTemplateRequest.class);
verify(client.admin().indices(), times(3)).putTemplate(argumentCaptor.capture(), anyObject());
ArgumentCaptor<PutComposableIndexTemplateAction.Request> argumentCaptor =
ArgumentCaptor.forClass(PutComposableIndexTemplateAction.Request.class);
verify(client, times(3)).execute(same(PutComposableIndexTemplateAction.INSTANCE), argumentCaptor.capture(), anyObject());
// now delete one template from the cluster state and lets retry
Map<String, Integer> existingTemplates = new HashMap<>();
@ -123,13 +129,13 @@ public class WatcherIndexTemplateRegistryTests extends ESTestCase {
existingTemplates.put(WatcherIndexTemplateRegistryField.TRIGGERED_TEMPLATE_NAME, INDEX_TEMPLATE_VERSION);
ClusterChangedEvent newEvent = createClusterChangedEvent(existingTemplates, nodes);
registry.clusterChanged(newEvent);
ArgumentCaptor<PutIndexTemplateRequest> captor = ArgumentCaptor.forClass(PutIndexTemplateRequest.class);
verify(client.admin().indices(), times(4)).putTemplate(captor.capture(), anyObject());
PutIndexTemplateRequest req = captor.getAllValues().stream()
argumentCaptor = ArgumentCaptor.forClass(PutComposableIndexTemplateAction.Request.class);
verify(client, times(3)).execute(same(PutComposableIndexTemplateAction.INSTANCE), argumentCaptor.capture(), anyObject());
PutComposableIndexTemplateAction.Request req = argumentCaptor.getAllValues().stream()
.filter(r -> r.name().equals(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME))
.findFirst()
.orElseThrow(() -> new AssertionError("expected the watch history template to be put"));
assertThat(req.settings().get("index.lifecycle.name"), equalTo("watch-history-ilm-policy"));
assertThat(req.indexTemplate().template().settings().get("index.lifecycle.name"), equalTo("watch-history-ilm-policy"));
}
public void testThatNonExistingTemplatesAreAddedEvenWithILMUsageDisabled() {
@ -141,8 +147,9 @@ public class WatcherIndexTemplateRegistryTests extends ESTestCase {
clusterService, threadPool, client, xContentRegistry);
ClusterChangedEvent event = createClusterChangedEvent(Settings.EMPTY, Collections.emptyMap(), Collections.emptyMap(), nodes);
registry.clusterChanged(event);
ArgumentCaptor<PutIndexTemplateRequest> argumentCaptor = ArgumentCaptor.forClass(PutIndexTemplateRequest.class);
verify(client.admin().indices(), times(3)).putTemplate(argumentCaptor.capture(), anyObject());
ArgumentCaptor<PutComposableIndexTemplateAction.Request> argumentCaptor =
ArgumentCaptor.forClass(PutComposableIndexTemplateAction.Request.class);
verify(client, times(3)).execute(same(PutComposableIndexTemplateAction.INSTANCE), argumentCaptor.capture(), anyObject());
// now delete one template from the cluster state and lets retry
Map<String, Integer> existingTemplates = new HashMap<>();
@ -151,7 +158,7 @@ public class WatcherIndexTemplateRegistryTests extends ESTestCase {
ClusterChangedEvent newEvent = createClusterChangedEvent(existingTemplates, nodes);
registry.clusterChanged(newEvent);
ArgumentCaptor<PutIndexTemplateRequest> captor = ArgumentCaptor.forClass(PutIndexTemplateRequest.class);
verify(client.admin().indices(), times(5)).putTemplate(captor.capture(), anyObject());
verify(client, times(3)).execute(same(PutComposableIndexTemplateAction.INSTANCE), argumentCaptor.capture(), anyObject());
captor.getAllValues().forEach(req -> assertNull(req.settings().get("index.lifecycle.name")));
verify(client, times(0)).execute(eq(PutLifecycleAction.INSTANCE), anyObject(), anyObject());
}
@ -262,9 +269,11 @@ public class WatcherIndexTemplateRegistryTests extends ESTestCase {
ClusterChangedEvent event = createClusterChangedEvent(existingTemplates, nodes);
registry.clusterChanged(event);
ArgumentCaptor<PutIndexTemplateRequest> argumentCaptor = ArgumentCaptor.forClass(PutIndexTemplateRequest.class);
verify(client.admin().indices(), times(1)).putTemplate(argumentCaptor.capture(), anyObject());
assertThat(argumentCaptor.getValue().name(), is(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_10));
ArgumentCaptor<PutComposableIndexTemplateAction.Request> argumentCaptor =
ArgumentCaptor.forClass(PutComposableIndexTemplateAction.Request.class);
verify(client, times(3)).execute(same(PutComposableIndexTemplateAction.INSTANCE), argumentCaptor.capture(), anyObject());
assertTrue(argumentCaptor.getAllValues().stream()
.anyMatch(r -> r.name().equals(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME)));
}
public void testThatTemplatesWithHiddenAreAppliedOnNewerNodes() {
@ -280,8 +289,9 @@ public class WatcherIndexTemplateRegistryTests extends ESTestCase {
registry.clusterChanged(event);
ArgumentCaptor<PutIndexTemplateRequest> argumentCaptor = ArgumentCaptor.forClass(PutIndexTemplateRequest.class);
verify(client.admin().indices(), times(1)).putTemplate(argumentCaptor.capture(), anyObject());
assertThat(argumentCaptor.getValue().name(), is(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_10));
verify(client.admin().indices(), atLeastOnce()).putTemplate(argumentCaptor.capture(), anyObject());
assertTrue(argumentCaptor.getAllValues().stream()
.anyMatch(i -> i.name().equals(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_10)));
existingTemplates.remove(".watch-history-6");
existingTemplates.put(".watch-history-10", 10);
@ -291,8 +301,16 @@ public class WatcherIndexTemplateRegistryTests extends ESTestCase {
registry.clusterChanged(event);
argumentCaptor = ArgumentCaptor.forClass(PutIndexTemplateRequest.class);
verify(client.admin().indices(), times(2)).putTemplate(argumentCaptor.capture(), anyObject());
assertThat(argumentCaptor.getValue().name(), is(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME));
verify(client.admin().indices(), atLeastOnce()).putTemplate(argumentCaptor.capture(), anyObject());
assertTrue(argumentCaptor.getAllValues().stream()
.anyMatch(i -> i.name().equals(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_10)));
ArgumentCaptor<PutComposableIndexTemplateAction.Request> captor =
ArgumentCaptor.forClass(PutComposableIndexTemplateAction.Request.class);
verify(client, atLeastOnce()).execute(same(PutComposableIndexTemplateAction.INSTANCE), captor.capture(), anyObject());
Set<String> templateNames =
captor.getAllValues().stream().map(PutComposableIndexTemplateAction.Request::name).collect(Collectors.toSet());
assertTrue(templateNames.contains(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME));
assertFalse(templateNames.contains(WatcherIndexTemplateRegistryField.HISTORY_TEMPLATE_NAME_10));
}
public void testThatTemplatesAreNotAppliedOnSameVersionNodes() {
@ -376,11 +394,14 @@ public class WatcherIndexTemplateRegistryTests extends ESTestCase {
private ClusterState createClusterState(Map<String, Integer> existingTemplates) {
Metadata.Builder metadataBuilder = Metadata.builder();
HashMap<String, ComposableIndexTemplate> templates = new HashMap<>();
for (Map.Entry<String, Integer> template : existingTemplates.entrySet()) {
metadataBuilder.put(IndexTemplateMetadata.builder(template.getKey())
.version(template.getValue())
.patterns(Arrays.asList(generateRandomStringArray(10, 100, false, false))));
ComposableIndexTemplate indexTemplate = mock(ComposableIndexTemplate.class);
when(indexTemplate.version()).thenReturn(template.getValue() == null ? null : (long) template.getValue());
when(indexTemplate.indexPatterns()).thenReturn(Arrays.asList(generateRandomStringArray(10, 100, false, false)));
templates.put(template.getKey(), indexTemplate);
}
metadataBuilder.indexTemplates(templates);
return ClusterState.builder(new ClusterName("foo")).metadata(metadataBuilder.build()).build();
}

View File

@ -39,7 +39,7 @@ public class WatcherRestartIT extends AbstractUpgradeTestCase {
// in a mixed cluster with some nodes <7.7.0 it will install template version 10, but if all nodes are <=7.7.0 template v11
// is used.
final String expectedMixedClusterTemplate = templatePrefix + (UPGRADE_FROM_VERSION.before(Version.V_7_7_0) ? "10" : "11");
final String expectedFinalTemplate = templatePrefix + "11";
final String expectedFinalTemplate = templatePrefix + "12";
if (ClusterType.MIXED == CLUSTER_TYPE) {
final Request request = new Request("HEAD", "/_template/" + expectedMixedClusterTemplate);
@ -50,7 +50,7 @@ public class WatcherRestartIT extends AbstractUpgradeTestCase {
Response response = client().performRequest(request);
assertThat(response.getStatusLine().getStatusCode(), is(200));
} else if (ClusterType.UPGRADED == CLUSTER_TYPE) {
Response response = client().performRequest(new Request("HEAD", "/_template/" + expectedFinalTemplate));
Response response = client().performRequest(new Request("HEAD", "/_index_template/" + expectedFinalTemplate));
assertThat(response.getStatusLine().getStatusCode(), is(200));
}
}