Elasticsearch 索引生命周期管理(ILM)实战指南

Elasticsearch 索引生命周期管理(ILM)实战指南

随着业务数据的持续增长,Elasticsearch 集群中的索引数量会呈爆炸式增长。如果不加以管理,海量索引不仅会消耗大量磁盘空间,还会拖慢集群的查询和写入性能。Elasticsearch 从 6.6 版本开始引入了索引生命周期管理(Index Lifecycle Management,ILM),让开发者可以用声明式策略自动管理索引从创建到删除的全过程。本文将从原理到实战,带你全面掌握 ILM。

一、为什么需要 ILM

1. 索引数量控制

在日志、监控等时序数据场景中,Elasticsearch 每天甚至每小时都会创建新索引。一个中等规模集群如果不加控制,几个月内就可能积累数万个索引。过多的索引会带来以下问题:

  • 集群状态(Cluster State)膨胀:所有索引的元数据都保存在集群状态中,索引过多会导致集群状态过大,影响节点间心跳和同步效率。
  • 分片管理开销:每个索引至少有一个分片,大量分片会耗尽节点的文件句柄和内存资源。
  • 查询性能下降:搜索请求需要遍历更多索引,协调节点的开销显著增加。

2. 存储成本优化

数据的热度是随时间递减的——刚刚产生的日志需要频繁查询(热数据),一周前的日志查询频率大幅降低(温数据),一个月前的日志几乎不再访问(冷数据)。为所有数据使用相同的存储策略是一种巨大的浪费。ILM 允许我们:

  • 热数据存放在 SSD 高性能节点上。
  • 温数据迁移到 HDD 普通节点。
  • 冷数据进一步压缩以节省空间。
  • 超过保留期限的数据自动删除。

据统计,通过合理的 ILM 策略,存储成本最高可降低 60%~80%
在引入 ILM 之前,很多团队使用 Elasticsearch Curator(一个独立的 Python 工具)通过定时任务完成类似工作。但 Curator 需要额外部署和维护,而 ILM 内嵌于 ES 引擎,配置更简洁、执行更可靠。

二、ILM 四个阶段:Hot → Warm → Cold → Delete

ILM 将索引的生命周期划分为最多 4 个阶段(Phase),每个阶段可以定义不同的 Action(动作)

阶段说明典型动作
Hot正在积极写入和查询的热数据rollover(滚动)、set_priority
Warm不再写入但还会被查询的温数据allocate(迁移)、forcemerge(段合并)、shrink(缩减分片)
Cold很少访问的冷数据,可接受较慢查询allocate(迁移到冷节点)、freezedownsample
Delete数据过期,彻底删除delete

索引在每个阶段停留的时间由 min_age 参数控制(从索引创建时开始计时),到达指定时间后会自动触发该阶段定义的动作。

三、配置示例:创建策略并关联到索引模板

1. 创建 ILM 策略

以下策略定义了:索引在 Hot 阶段停留 7 天后滚动;滚动后进入 Warm 阶段,合并段并迁移到 warm 节点;30 天后进入 Cold 阶段;60 天后删除。

PUT _ilm/policy/nginx_logs_policy
{
  "policy": {
    "phases": {
      "hot": {
        "min_age": "0ms",
        "actions": {
          "rollover": {
            "max_size": "50GB",
            "max_age": "7d"
          },
          "set_priority": {
            "priority": 100
          }
        }
      },
      "warm": {
        "min_age": "7d",
        "actions": {
          "forcemerge": {
            "max_num_segments": 1
          },
          "allocate": {
            "require": {
              "data": "warm"
            }
          },
          "set_priority": {
            "priority": 50
          }
        }
      },
      "cold": {
        "min_age": "30d",
        "actions": {
          "allocate": {
            "require": {
              "data": "cold"
            }
          },
          "set_priority": {
            "priority": 0
          }
        }
      },
      "delete": {
        "min_age": "60d",
        "actions": {
          "delete": {}
        }
      }
    }
  }
}

2. 创建索引模板关联策略

将策略绑定到索引模板,这样所有匹配 nginx-logs-* 的新索引都会自动应用该策略:

PUT _index_template/nginx_logs_template
{
  "index_patterns": ["nginx-logs-*"],
  "template": {
    "settings": {
      "number_of_shards": 3,
      "number_of_replicas": 1,
      "index.lifecycle.name": "nginx_logs_policy",
      "index.lifecycle.rollover_alias": "nginx-logs"
    }
  }
}

四、Rollover 滚动索引机制

Rollover(滚动)是 ILM 中最核心的机制之一,它解决的是"单个索引过大"的问题。当写入索引满足指定条件时,ILM 会自动:

  • 创建一个新索引作为写入别名的新目标。
  • 将旧的索引标记为只读,等待进入下一阶段。

Rollover 的触发条件可以组合使用:

"rollover": {
  "max_size": "50GB",      // 索引大小超过 50GB
  "max_age": "7d",         // 索引创建超过 7 天
  "max_docs": 10000000     // 文档数超过 1000 万
}

多个条件之间是 OR(或) 关系——任何一个条件满足就会触发滚动。首次创建写入索引时需要手动设置别名:

PUT nginx-logs-000001
{
  "aliases": {
    "nginx-logs": {
      "is_write_index": true
    }
  }
}

之后应用系统统一向别名 nginx-logs 写入数据,ILM 会自动完成滚动。

五、冷热数据架构(node.attr.data 配置)

要实现数据在不同阶段迁移到不同性能的节点,需要先对节点打标签。Elasticsearch 通过 node.attr 实现自定义节点属性。

1. 节点配置

elasticsearch.yml 中为每个节点设置属性:

# hot 节点(SSD,高性能)
node.attr.data: hot

# warm 节点(普通 HDD)
node.attr.data: warm

# cold 节点(大容量 HDD,可配置便宜存储)
node.attr.data: cold

2. 验证节点属性

配置完成后,通过 API 验证:

GET _cat/nodeattrs?v&h=node,attr,value

输出示例:

node1    data    hot
node2    data    warm
node3    data    cold

3. 拓扑建议

  • 至少 2 个 Hot 节点:保证写入高可用,建议使用 SSD。
  • 2~4 个 Warm 节点:用于承载温数据查询,普通 HDD 即可。
  • 2~N 个 Cold 节点:大容量 HDD,可配置较少的 CPU 和内存资源。
  • Dedicated Master 节点:建议独立部署,不承担数据角色。

ILM 策略中的 allocate 动作会通过 require 条件匹配这些标签,自动将索引迁移到对应节点。

六、ILM 与 Curator 的对比

在 ILM 出现之前,Elasticsearch Curator 是管理索引生命周期的主流工具。以下是两者的详细对比:

维度ILMCurator
架构内置于 ES 引擎,无需额外组件独立 Python 工具,需额外部署和定时调度(cron)
配置方式声明式 API(RESTful JSON)YAML 或命令行动作
实时性Master 节点自动检查并执行,延迟低依赖 cron 调度频率(通常每小时执行一次)
Rollover原生支持,自动滚动索引不支持自动滚转,需手动或借助 alias 操作
冷热迁移通过 allocate action 自动完成通过 action.routing.allocation.require 手动指定
可视化Kibana 提供 ILM 管理界面
灵活性策略固定,动作类型有限动作丰富,支持 snapshots、replicas、close 等
适用版本Elasticsearch 6.6+所有版本,尤其适合 ES 6.6 之前的集群

结论:如果你的集群版本 ≥ 7.x,强烈推荐使用 ILM;对于无法升级的老集群或需要复杂快照管理的场景,Curator 仍是一个可选的补充工具。

七、实际案例:Nginx 日志按天轮转、30 天后删除

下面是一个完整的生产级 Nginx 日志管理方案,每天自动滚动索引,保留 30 天后删除。

1. 创建 ILM 策略

PUT _ilm/policy/nginx_daily_policy
{
  "policy": {
    "phases": {
      "hot": {
        "min_age": "0ms",
        "actions": {
          "rollover": {
            "max_age": "1d",
            "max_size": "30GB"
          },
          "set_priority": {
            "priority": 100
          }
        }
      },
      "delete": {
        "min_age": "30d",
        "actions": {
          "delete": {}
        }
      }
    }
  }
}

2. 索引模板与初始索引

PUT _index_template/nginx_daily_template
{
  "index_patterns": ["nginx-logs-*"],
  "template": {
    "settings": {
      "number_of_shards": 3,
      "number_of_replicas": 1,
      "index.lifecycle.name": "nginx_daily_policy",
      "index.lifecycle.rollover_alias": "nginx-logs",
      "routing.allocation.require.data": "hot"
    },
    "mappings": {
      "properties": {
        "@timestamp": { "type": "date" },
        "remote_addr": { "type": "ip" },
        "request": { "type": "text" },
        "status": { "type": "integer" },
        "body_bytes_sent": { "type": "long" },
        "http_user_agent": { "type": "text" },
        "request_time": { "type": "float" }
      }
    }
  }
}

PUT nginx-logs-000001
{
  "aliases": {
    "nginx-logs": {
      "is_write_index": true
    }
  }
}

3. 接入流程

  • FilebeatLogstash 采集 Nginx 日志,指定 Elasticsearch 输出到别名 nginx-logs
  • ILM 每天触发 rollover,创建 nginx-logs-000002 等新索引。
  • 旧索引在创建满 30 天后进入 delete 阶段,自动删除。

4. 验证与监控

使用以下命令查看 ILM 执行状态:

# 查看策略执行情况
GET _ilm/policy/nginx_daily_policy

# 查看特定索引处于哪个阶段
GET nginx-logs-000001/_ilm/explain

# Kibana 中查看
# Stack Management → Index Lifecycle Policies

总结

Elasticsearch ILM 是管理时序数据的利器。通过 Hot → Warm → Cold → Delete 四个阶段的自动流转,结合 Rollover 滚动索引和冷热节点部署,可以显著降低存储成本、简化运维工作、保障集群性能。相比 Curator,ILM 的声明式配置更简洁、实时性更高,是 Elastic Stack 用户的最佳选择。

实战中需要注意:合理设置 Rollover 条件(避免滚动过于频繁或过慢);冷热节点属性要提前规划;ILM 策略创建后不可修改部分关键参数如 max_age(需要删除重建)。掌握这些要点,你就能在生产环境中自信地部署 ILM 了。


系列文章导航
← 上一篇:Elasticsearch 集群监控与报警实战
下一篇:Elasticsearch SQL 查询与 JDBC 集成 →

发表回复

后才能评论