📣 极限科技诚招搜索运维工程师(Elasticsearch/Easysearch)- 全职/北京 👉 : 立即申请加入

在现代企业的 IT 架构中,日志数据往往占据了数据存储的"半壁江山"。从应用程序日志、网关日志到基础设施监控指标,这些时序数据(Time Series Data)具有写入量大、只有追加操作(Append-only)、随时间推移价值递减的特点。

传统的管理方式通常是按天生成索引(如 logs-2023-10-01),但这带来了管理上的复杂性:如何自动化清理旧数据?如何处理某天流量暴增导致单个索引过大的问题?查询时如何避免编写复杂的通配符?

INFINI Easysearch 支持原生的 Data Stream(数据流) 功能,结合其独有的 ZSTD 压缩技术,为海量日志管理提供了一套既简单又高效的解决方案。本文将带你深入了解并实战 Easysearch 的数据流管理。

什么是 Data Stream? #

Data Stream 是 Elasticsearch(Easysearch 完全兼容)引入的一种抽象概念,专门用于简化时序数据的管理。

即使用户看到的是一个统一的名称(例如 logs-prod),但在后台,Easysearch 自动维护了一个隐藏的索引列表(Backing Indices)。

  • 写入时:数据总是写入最新的那个"写索引"。
  • 查询时:请求会自动路由到所有包含相关数据的索引上。
  • 滚动(Rollover):配合索引生命周期管理(ILM),当"写索引"达到一定大小或时间(如 50GB 或 7天)后,会自动创建一个新的写索引,旧索引转为只读。

简单来说,Data Stream 让你不再需要关心具体的索引名称和切分逻辑,只需对着一个名字读写即可。

为什么在 Easysearch 中使用 Data Stream? #

除了简化运维,Easysearch 的核心优势能让 Data Stream 方案发挥更大价值:

  1. 极致压缩(降本):日志数据通常重复率高。Easysearch 支持 ZSTD 压缩算法(ZSTD),结合 Data Stream 的自动滚动机制,可以将旧数据的存储成本降低 40%-50%。
  2. 写入稳定性:Easysearch 对写入进行了深度优化,能够承受 Data Stream 场景下高并发的日志吞吐,不易出现节点 Crash 或 OOM。
  3. 生命周期自动化:通过 ILM 策略,自动完成从 热(Hot)-> 温(Warm)-> 冷(Cold)-> 删除 的全生命周期流转。

实战:配置 Easysearch Data Stream #

下面我们通过一个完整的示例,演示如何创建一个用于存储 Nginx 日志的数据流,并应用生命周期策略。

第一步:创建索引生命周期策略 (ILM Policy) #

首先,我们需要定义数据的"生老病死"。假设我们的策略如下:

  • Hot 阶段:索引大小达到 30GB 或创建时间超过 1 天,则滚动生成新索引。
  • Warm 阶段:滚动后立即进入 Warm 阶段,设为只读。
  • Delete 阶段:数据保留 30 天后自动删除。
PUT _ilm/policy/logs_policy
{
  "policy": {
    "phases": {
      "hot": {
        "min_age": "0ms",
        "actions": {
          "rollover": {
            "max_size": "30gb",
            "max_age": "1d"
          }
        }
      },
      "warm": {
        "min_age": "0ms",
        "actions": {
          "readonly": {}
        }
      },
      "delete": {
        "min_age": "30d",
        "actions": {
          "delete": {}
        }
      }
    }
  }
}

第二步:创建组件模板 (Component Templates) #

为了复用配置,我们建议使用组件模板。这里我们将配置映射(Mappings)**和**设置(Settings)

关键点:在这里我们开启 Easysearch 的 ZSTD 压缩,这是降本的关键配置。

# 1. 配置 Settings,启用 ZSTD 压缩
PUT _component_template/logs_settings
{
  "template": {
    "settings": {
      "number_of_shards": 3,
      "number_of_replicas": 1,
      "index.lifecycle.name": "logs_policy",
      "index.codec": "ZSTD"
    }
  }
}

# 2. 配置 Mappings,定义字段结构
PUT _component_template/logs_mappings
{
  "template": {
    "mappings": {
      "properties": {
        "@timestamp": {
          "type": "date"
        },
        "host": {
          "type": "keyword"
        },
        "message": {
          "type": "text"
        },
        "status_code": {
          "type": "integer"
        }
      }
    }
  }
}

第三步:创建索引模板 (Index Template) #

这是最重要的一步。我们需要创建一个索引模板,将上面的组件组合起来,并显式启用 data_stream 模式。

PUT _index_template/logs_template
{
  "index_patterns": [
    "logs-nginx-*"
  ],
  "data_stream": {},
  "composed_of": [
    "logs_settings",
    "logs_mappings"
  ],
  "priority": 100
}

第四步:创建 Data Stream 并写入数据 #

配置完成后,我们不需要显式调用 “Create Data Stream” 的 API。当我们第一次向匹配 index_patterns 的名称写入数据时,Data Stream 会自动创建。

注意:Data Stream 强制要求文档必须包含 @timestamp 字段。

# 写入第一条数据,Easysearch 会自动创建名为 logs-nginx-prod  Data Stream
POST logs-nginx-prod/_doc
{
  "@timestamp": "2023-10-27T10:00:00Z",
  "host": "web-server-01",
  "message": "GET /index.html 200",
  "status_code": 200
}

第五步:验证与管理 #

写入成功后,我们可以查看 Data Stream 的状态:

GET _data_stream/logs-nginx-prod

返回结果将显示该流背后的具体索引(如 .ds-logs-nginx-prod-000001)。

如果需要查询数据,直接使用 Data Stream 的名称,就像操作普通索引一样:

GET logs-nginx-prod/_search
{
  "query": {
    "match": {
      "status_code": 200
    }
  }
}

Data Stream 的限制与注意事项 #

在使用 Easysearch Data Stream 时,有几点需要注意:

  1. 仅限追加(Append-Only):Data Stream 设计初衷是处理时序数据,因此不支持直接更新(Update)已存在的文档。如果确实需要修改旧数据,必须通过 _update_by_query 或者直接对背后的具体索引进行操作(不推荐)。
  2. 必须包含时间戳:写入的文档必须包含 @timestamp 字段(或者在映射中定义好的自定义时间字段)。
  3. 删除操作:你不能直接删除 Data Stream 中的某条文档,但可以使用 delete_by_query。通常建议依赖 ILM 策略自动删除过期的整个索引,效率最高。

总结 #

通过在 INFINI Easysearch 中使用 Data Stream,我们实现了日志管理的"自动驾驶":

  • 运维侧:无需编写脚本每天创建索引,无需手动删除旧数据,ILM 策略全自动接管。
  • 开发侧:读写入口统一,不再受限于 logs-YYYY-MM-DD 这种日期命名的困扰。
  • 成本侧:利用 Easysearch 的 ZSTD 压缩,在不改变业务逻辑的前提下,大幅节省存储空间(通常可达 50%)。

对于任何需要处理大量时序日志、监控指标的企业,Easysearch Data Stream + ILM + ZSTD 都是目前的最佳实践组合。