mcpField
E
elasticsearch-authz

elasticsearch-authz

github.com/elastic安全6022.9k 次安装今天更新
代码仓库

关于 elasticsearch-authz

用于管理 Elasticsearch 基于角色的访问控制的技能,涵盖用户、角色、角色分配及外部 Realm 映射。适合负责集群权限配置的团队,可设置索引和 Kibana 权限,并通过文档级、字段级安全与模板实现细粒度控制。

主要功能

  1. 01管理原生用户和角色
  2. 02分配用户角色并验证权限
  3. 03配置 Kibana 功能与空间权限
  4. 04映射外部 Realm 用户
  5. 05设置文档级和字段级安全
  6. 06使用模板实现属性访问控制

适用场景

  1. 01为用户配置特定索引的只读权限
  2. 02限制不同部门可查看的文档
  3. 03隐藏角色不可见的敏感字段
  4. 04根据 LDAP 或 SAML 属性映射角色

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/elastic/agent-skills --skill elasticsearch-authz

安装后在 Claude Code 中输入/elasticsearch-authz确认已加载。

附带文件references/api-reference.mdreferences/deployment-compatibility.md

详细介绍

Elasticsearch 授权

管理 Elasticsearch 基于角色的访问控制:原生用户、角色、角色分配,以及外部领域的角色映射。

如需了解身份验证方法和 API 密钥管理,请参阅 elasticsearch-authn 技能。

如需查看详细的 API 端点,请参阅 references/api-reference.md。

部署说明: 自行管理、ECH 和 Serverless 的功能可用性有所不同。详情请参阅 部署兼容性。

待办事项

  • 创建具有特定权限集的原生用户
  • 定义具有最小权限索引和集群访问权限的自定义角色
  • 为现有用户分配一个或多个角色
  • 创建具有 Kibana 功能或空间权限的角色
  • 为外部领域用户(SAML、LDAP、PKI)配置角色映射
  • 根据用户属性动态派生角色分配(Mustache 模板)
  • 按用户或部门限制文档可见性(文档级安全)
  • 对某些角色隐藏 PII 等敏感字段(字段级安全)
  • 使用模板化角色查询实现基于属性的访问控制(ABAC)
  • 将自然语言访问请求转换为用户、角色和角色映射任务

先决条件

项目说明
Elasticsearch URL集群端点(例如 https://localhost:9200 或云部署 URL)
Kibana URL仅在设置 Kibana 功能/空间权限时需要
身份验证有效凭据(请参阅 elasticsearch-authn 技能)
集群权限用户和角色管理操作需要 manage_security

如有任何缺失值,请向用户询问。

分解访问请求

当用户用自然语言描述访问需求时(例如“创建一个对 logs-* 具有只读访问权限的用户”),请先将请求拆分为具体任务,再执行。遵循以下工作流:

步骤 1 — 确定组成部分

从提示词中提取以下信息:

组成部分需要回答的问题
对象新建的原生用户、现有用户,还是外部领域用户(LDAP、SAML 等)?
内容哪些索引、数据流或 Kibana 功能?
访问级别读取、写入、管理,还是特定的权限集?
范围所有文档/字段,还是按地区、部门、敏感级别限制?
Kibana?请求是否提及任何 Kibana 功能(仪表板、Discover 等)?
部署?自行管理、ECH 还是 Serverless?Serverless 使用不同的用户模型。
步骤 2 — 检查现有角色

创建新角色之前,请检查现有角色是否已授予所需访问权限:

curl "${ELASTICSEARCH_URL}/_security/role" <auth_flags>

如果存在匹配的角色,请跳过角色创建并重复使用该角色。

步骤 3 — 创建角色(如有需要)

根据请求确定角色名称和显示名称。对于纯索引/集群角色,请使用 Elasticsearch API。如果涉及 Kibana 功能,请使用 Kibana API(请参阅选择合适的 API)。

第 4 步 — 创建或更新用户
场景操作
新建本地用户使用该角色和生成的强密码创建用户。(仅限自管理 / ECH。)
现有本地用户获取当前角色,追加新角色,然后使用完整数组更新用户。(仅限自管理 / ECH。)
外部 Realm 用户创建角色映射,将用户的 Realm 属性与角色相匹配。(仅限自管理 / ECH。)
Serverless 用户使用 cloud-access-management 技能。先分配预定义角色或创建自定义角色,然后通过 Cloud API 分配该角色。
示例拆解

提示词:“创建一个用户 analyst,使其对 logs-* 和 metrics-* 具有只读访问权限,并能在 Kibana 中查看仪表板。”

  1. 确认信息:新用户 analyst、索引 logs-*/metrics-*、仪表板、读取权限。
  2. 检查角色:GET /_security/role — 没有匹配项。
  3. 通过 Kibana API 创建角色(涉及仪表板):logs-metrics-dashboard-viewer。
  4. 创建用户:通过 POST /_security/user/analyst,并设置 roles: ["logs-metrics-dashboard-viewer"]。

如果请求含糊不清,请在每个步骤中向用户确认。

管理本地用户

本地用户管理适用于自管理和 ECH 部署。在 Serverless 上,用户由组织级别管理 — 请跳过本节。

创建用户
curl -X POST "${ELASTICSEARCH_URL}/_security/user/${USERNAME}" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "password": "'"${PASSWORD}"'",
    "roles": ["'"${ROLE_NAME}"'"],
    "full_name": "'"${FULL_NAME}"'",
    "email": "'"${EMAIL}"'",
    "enabled": true
  }'
更新用户

使用 PUT /_security/user/${USERNAME} 并提供要更改的字段。省略 password 可保留现有密码。

其他用户操作
curl -X POST "${ELASTICSEARCH_URL}/_security/user/${USERNAME}/_password" \
  <auth_flags> -H "Content-Type: application/json" \
  -d '{"password": "'"${NEW_PASSWORD}"'"}'
curl -X PUT "${ELASTICSEARCH_URL}/_security/user/${USERNAME}/_disable" <auth_flags>
curl -X PUT "${ELASTICSEARCH_URL}/_security/user/${USERNAME}/_enable" <auth_flags>
curl "${ELASTICSEARCH_URL}/_security/user/${USERNAME}" <auth_flags>
curl -X DELETE "${ELASTICSEARCH_URL}/_security/user/${USERNAME}" <auth_flags>

管理角色

选择合适的 API

如果角色只需要 cluster 和 indices 权限,请使用 Elasticsearch API(PUT /_security/role/{name})。这是默认选项 — 无需 Kibana 端点。

如果角色包含任何 Kibana 功能或空间权限,请使用 Kibana 角色 API(PUT /api/security/role/{name})。Elasticsearch API 无法设置 Kibana 功能授权、空间范围或基本权限,因此,如果用户提到 Discover、Dashboards、Maps、Visualize、Canvas 或其他任何 Kibana 应用,则必须使用 Kibana API。

如果 Kibana 端点不可用,或向 Kibana 进行 API 密钥身份验证失败,则退回使用 Elasticsearch API 设置 cluster 和 indices 部分,并告知用户无法设置 Kibana 权限。在放弃之前,请用户提供 Kibana URL 或其他凭据。

创建或更新角色(Elasticsearch API)

当角色仅包含索引和集群权限时,默认选择:

curl -X PUT "${ELASTICSEARCH_URL}/_security/role/${ROLE_NAME}" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "description": "'"${ROLE_DISPLAY_NAME}"'",
    "cluster": [],
    "indices": [
      {
        "names": ["'"${INDEX_PATTERN}"'"],
        "privileges": ["read", "view_index_metadata"]
      }
    ]
  }'
创建或更新角色(Kibana API)

当角色包含 Kibana 功能或空间权限时,必须使用:

curl -X PUT "${KIBANA_URL}/api/security/role/${ROLE_NAME}" \
  <auth_flags> \
  -H "kbn-xsrf: true" \
  -H "Content-Type: application/json" \
  -d '{
    "description": "'"${ROLE_DISPLAY_NAME}"'",
    "elasticsearch": {
      "cluster": [],
      "indices": [
        {
          "names": ["'"${INDEX_PATTERN}"'"],
          "privileges": ["read", "view_index_metadata"]
        }
      ]
    },
    "kibana": [
      {
        "base": [],
        "feature": {
          "discover": ["read"],
          "dashboard": ["read"]
        },
        "spaces": ["*"]
      }
    ]
  }'
获取、列出和删除角色
curl "${ELASTICSEARCH_URL}/_security/role/${ROLE_NAME}" <auth_flags>
curl "${ELASTICSEARCH_URL}/_security/role" <auth_flags>
curl -X DELETE "${ELASTICSEARCH_URL}/_security/role/${ROLE_NAME}" <auth_flags>

文档级和字段级安全

角色可以在索引内限制对文档和字段的访问,权限范围比索引级权限更精细。

字段级安全(FLS)

限制角色可见的字段。使用 grant 将字段加入允许列表,或使用 except 将字段加入屏蔽列表:

curl -X PUT "${ELASTICSEARCH_URL}/_security/role/pii-redacted-reader" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "description": "PII Redacted Reader",
    "indices": [
      {
        "names": ["customers-*"],
        "privileges": ["read"],
        "field_security": {
          "grant": ["*"],
          "except": ["ssn", "credit_card", "date_of_birth"]
        }
      }
    ]
  }'

具有此角色的用户可以看到除 PII 字段以外的所有字段。FLS 会对搜索、获取和聚合结果强制执行。

文档级安全(DLS)

通过附加查询过滤器来限制角色可见的文档:

curl -X PUT "${ELASTICSEARCH_URL}/_security/role/emea-logs-reader" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "description": "EMEA Logs Reader",
    "indices": [
      {
        "names": ["logs-*"],
        "privileges": ["read"],
        "query": "{\"term\": {\"region\": \"emea\"}}"
      }
    ]
  }'

query 字段是一个包含 Query DSL 过滤器的 JSON 字符串。具有此角色的用户只能看到 region 等于 emea 的文档。

模板化 DLS 查询(ABAC)

DLS 查询支持 Mustache 模板,可在查询时注入用户元数据,从而在 RBAC 之上实现基于属性的访问控制 (ABAC)。将用户专属属性存储在用户的 metadata 字段中,然后在角色 查询模板中使用 {{_user.metadata.<key>}} 引用。

curl -X PUT "${ELASTICSEARCH_URL}/_security/role/department-reader" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "description": "Department Reader",
    "indices": [
      {
        "names": ["records-*"],
        "privileges": ["read"],
        "query": "{\"template\": {\"source\": \"{\\\"term\\\": {\\\"department\\\": \\\"{{_user.metadata.department}}\\\"}}\"}}"
      }
    ]
  }'

具有 "metadata": {"department": "engineering"} 的用户只能看到 department 等于 engineering 的文档。同一个 角色适用于所有部门,无需为每个部门创建单独的角色。

对于多值属性(例如,必需项目的列表),可使用 terms_set 和 minimum_should_match_field,以 确保用户持有文档中列出的所有必需属性。这样,只需使用单个角色,即可实现复杂的 ABAC 策略,例如组合 安全级别、项目列表和认证日期。完整的 terms_set ABAC 示例(包括组合多条件策略和用户元数据设置),请参阅 references/api-reference.md。

组合使用 DLS 和 FLS

单个索引权限条目可以同时包含 query(DLS)和 field_security(FLS)。实际组合用例请参阅 HR 部门示例。

当用户持有多个角色时,DLS 查询会以 OR 组合,FLS 授权字段会合并。没有 DLS/FLS 限制的宽泛角色可能会意外扩大访问范围。组合角色时,务必检查最终生效的权限,并确保不受限制的角色不会覆盖 DLS/FLS 的预期限制。

为用户分配角色

仅适用于自托管和 ECH。在 Serverless 上,请使用 cloud-access-management 技能 — 参阅 Serverless 用户访问。

使用新的 roles 数组更新用户:

curl -X PUT "${ELASTICSEARCH_URL}/_security/user/${USERNAME}" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "roles": ["role-a", "role-b"]
  }'

roles 数组会被整体替换 — 请包含用户应拥有的所有角色。更新前先获取用户信息,以查看当前角色。

验证生效的权限

更新角色或用户后,使用以下命令验证实际访问权限:

curl -X POST "${ELASTICSEARCH_URL}/_security/user/_has_privileges" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "cluster": ["monitor"],
    "index": [
      {
        "names": ["'"${INDEX_PATTERN}"'"],
        "privileges": ["read", "view_index_metadata"]
      }
    ]
  }'

管理角色映射

Serverless 上不提供角色映射(ES API 和 Kibana UI 均已禁用)。请改用 cloud-access-management 技能 — 参阅 Serverless 用户访问。

角色映射会根据属性规则,将外部领域用户(LDAP、AD、SAML、PKI)分配给角色。仅适用于自托管和 ECH。 支持的规则运算符和资源字段,请参阅 角色映射资源属性。

静态角色映射
curl -X PUT "${ELASTICSEARCH_URL}/_security/role_mapping/saml-default-access" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "roles": ["viewer"],
    "enabled": true,
    "rules": {
      "field": { "realm.name": "saml1" }
    }
  }'
基于 LDAP 组的映射
curl -X PUT "${ELASTICSEARCH_URL}/_security/role_mapping/ldap-admins" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "roles": ["superuser"],
    "enabled": true,
    "rules": {
      "all": [
        { "field": { "realm.name": "ldap1" } },
        { "field": { "groups": "cn=admins,ou=groups,dc=example,dc=com" } }
      ]
    }
  }'
使用 Mustache 模板动态分配角色

使用 role_templates 而非 roles,根据用户属性推导角色名称。必须启用脚本功能。

curl -X PUT "${ELASTICSEARCH_URL}/_security/role_mapping/ldap-group-roles" \
  <auth_flags> \
  -H "Content-Type: application/json" \
  -d '{
    "role_templates": [
      {
        "template": { "source": "{{#tojson}}groups{{/tojson}}" },
        "format": "json"
      }
    ],
    "enabled": true,
    "rules": {
      "field": { "realm.name": "ldap1" }
    }
  }'

更多 Mustache 模式示例(包括根据领域用户名推导角色和分级组访问),请参阅 references/api-reference.md。

获取、列出和删除角色映射
curl "${ELASTICSEARCH_URL}/_security/role_mapping/saml-default-access" <auth_flags>
curl "${ELASTICSEARCH_URL}/_security/role_mapping" <auth_flags>
curl -X DELETE "${ELASTICSEARCH_URL}/_security/role_mapping/saml-default-access" <auth_flags>

Serverless 用户访问

在 Serverless 上,没有原生用户或角色映射。用户通过 Cloud 级别的角色分配获得项目访问权限。

  • 预定义角色(例如 admin、developer、viewer)适用于常见访问场景。如果其中一个符合需求,可直接通过 Cloud API 分配 — 无需创建自定义角色。
  • 当用户需要精细化访问权限(特定索引、Kibana 功能、DLS/FLS)时,必须使用自定义角色。 使用 Elasticsearch API 或 Kibana API 创建自定义角色(与自托管相同 — 请参阅 管理角色),然后通过 Cloud API 将其与预定义基础角色一同分配给用户。
  • Serverless 自定义角色不提供 Run-as 权限。

完整工作流(邀请用户、分配角色、管理 Cloud API 密钥和验证访问权限)请使用 cloud-access-management 技能。此技能仅处理角色定义;cloud-access-management 负责用户分配。

示例

创建用于查看日志的只读用户

请求:“创建一个用户 joe,使其拥有对 logs-* 的只读访问权限。”

  1. 通过 PUT /_security/role/logs-reader 创建角色,并设置 "description": "Logs Reader" 和 indices: [{ names: ["logs-*"], privileges: ["read", "view_index_metadata"] }]。
  2. 通过 POST /_security/user/joe 创建用户,并设置 "roles": ["logs-reader"] 和一个强度高的生成密码。
创建可访问 Kibana 仪表板的角色

请求:“允许用户读取 logs-*,并在 Kibana 中查看仪表板。”

使用 Kibana API(PUT <KIBANA_URL>/api/security/role/logs-dashboard-viewer),通过 elasticsearch.indices 设置数据访问权限,并通过 kibana[].feature 设置对所有空间中仪表板和 Discover 的只读访问权限。完整请求结构请参阅 创建或更新角色(Kibana API)。

为现有用户添加角色

请求:“在 Alice 现有角色的基础上,授予她对 apm-* 的访问权限。”

  1. GET /_security/user/alice — 响应显示 "roles": ["viewer"]。
  2. 创建 apm-reader 角色,并设置 indices: [{ names: ["apm-*"], privileges: ["read", "view_index_metadata"] }]。
  3. 使用 "roles": ["viewer", "apm-reader"] 执行 PUT /_security/user/alice(包括所有角色)。
授予 Serverless 用户对 Kibana 仪表板的读写访问权限

请求:“授予 [email protected] 对 colors 索引的读写访问权限,并允许她使用仪表板和 Discover。”

  1. 通过 Kibana API 创建自定义角色:PUT <KIBANA_URL>/api/security/role/colors-rw-kibana,通过 elasticsearch.indices 为 colors 设置 read、write、view_index_metadata 权限,并通过 kibana[].feature 设置 dashboard、discover 权限。
  2. 使用 cloud-access-management 技能为该用户分配自定义角色 colors-rw-kibana。
按部门限制 HR 数据(DLS + FLS)

请求:“每位经理只能查看自己部门的 HR 记录,并且应隐藏个人身份信息字段。”

  1. 创建带部门元数据的用户:POST /_security/user/manager_a,并设置 "metadata": {"department": "engineering"}。
  2. 创建具有 DLS + FLS 的角色:
PUT /_security/role/hr-department-viewer
{
  "description": "HR Department Viewer",
  "indices": [
    {
      "names": ["hr-*"],
      "privileges": ["read"],
      "field_security": { "grant": ["*"], "except": ["ssn", "salary", "date_of_birth"] },
      "query": "{\"template\": {\"source\": \"{\\\"term\\\": {\\\"department\\\": \\\"{{_user.metadata.department}}\\\"}}\"}}"
    }
  ]
}

同一角色适用于所有部门 — 每位用户只能看到自己部门的记录,且个人身份信息字段会被移除。

指南

最小权限原则
  • 日常操作绝不要使用 elastic 超级用户。应创建专用的最小权限角色,并将 elastic 保留用于初始设置和紧急恢复。
  • 使用 read 和 view_index_metadata 进行只读数据访问。除非有明确需要,否则不要设置 cluster 权限。
  • 使用 DLS(query)和 FLS(field_security)限制对索引内数据的访问。
仅使用命名权限

绝不要使用内部操作名称(例如 indices:data/read/search)。始终使用官方文档中列出的命名权限。 优先使用细粒度权限(manage_ingest_pipelines、monitor),而不是宽泛权限(manage、all)。完整的权限参考表请参阅 references/api-reference.md。

角色命名约定
  • 使用简短的小写名称,并以连字符分隔:logs-reader、apm-data-viewer、metrics-writer。
  • 避免使用 custom-role 或 new-role 之类的通用名称。
  • 将 description 设为简短、易读的显示名称,而不是长句。它会在 Kibana UI 中显示为角色标签。好的示例:"Logs Reader"、"APM Data Viewer"。不好的示例: "Read-only access to all logs-* indices for the operations team"。
用户管理
  • 默认生成强密码:至少 16 个字符,混合使用大写字母、小写字母、数字和符号(例如 X9k#mP2vL!qR7wZn)。绝不要使用 changeme 或 password123 之类的占位值。
  • 优先停用用户,而不是删除用户,以保留审计记录。
  • 更新用户时,roles 数组会被完全替换。修改前务必获取当前角色。
角色映射最佳实践
  • 对于简单、固定的分配(例如,所有 SAML 用户都获得 viewer 角色),使用静态 roles。
  • 仅当角色必须根据用户属性动态生成时,才使用带 Mustache 的 role_templates。
  • 组合使用 all、any、field 和 except 规则,以表达复杂条件,避免重复映射。
  • 先使用 enabled: false 测试新映射,验证通过后再启用。

部署兼容性

请参阅 references/deployment-compatibility.md,了解功能矩阵以及关于自管理、ECH 和 Serverless 部署差异的详细说明。

评论

支持 Markdown