3. 租户隔离概念:多租户模型、数据隔离策略与隔离粒度选择
在可观测性平台中,租户隔离是保障多团队、多业务线或不同客户共享同一套观测基础设施时,数据安全与操作边界清晰的核心机制。缺乏合理的隔离设计,会导致链路数据交叉污染、指标误读、告警风暴波及无关方,甚至引发合规风险。
本章从三个维度拆解租户隔离:多租户模型(谁在用)、数据隔离策略(怎么隔)、隔离粒度选择(隔到多细)。
3.1 多租户模型:三种主流架构
多租户模型决定了租户在平台中的身份标识、资源归属与权限边界。在 OTel 链路追踪场景下,常见三种模型:
| 模型 | 核心特征 | 适用场景 | 典型代表 |
|---|---|---|---|
| 独立实例模型 | 每个租户拥有独立的 Collector、存储后端、查询服务 | 金融、医疗等强合规行业;租户间完全物理隔离 | 每个客户独享一套 Jaeger + Elasticsearch |
| 共享实例模型 | 所有租户共享 Collector 与存储,通过租户 ID 字段区分数据 | 内部多团队、SaaS 平台;追求资源利用率 | Grafana Tempo + 租户标签路由 |
| 混合模型 | 部分租户独享实例(高安全),其余共享实例(低成本) | 大型企业分级管理;核心业务与普通业务混合部署 | 核心交易链路独享 Collector,日志/指标共享 |
实践建议:在 OTel 链路追踪中,共享实例模型是主流选择。通过
Resource 属性中的 tenant.id 或 service.namespace 实现逻辑隔离,成本低且扩展灵活。
3.2 数据隔离策略:物理、逻辑与混合
数据隔离策略决定了租户数据在存储、传输与查询阶段的分离程度。在 OTel 链路追踪中,三种策略各有优劣:
| 策略 | 实现方式 | 安全等级 | 资源开销 | 运维复杂度 |
|---|---|---|---|---|
| 物理隔离 | 独立数据库/独立索引/独立 Collector 进程 | ★★★★★ | 高(N 倍资源) | 高(多实例管理) |
| 逻辑隔离 | 共享存储 + 租户标签 + 查询过滤 + RBAC | ★★★☆☆ | 低(共享资源) | 中(标签治理) |
| 混合隔离 | 核心租户物理隔离 + 普通租户逻辑隔离 | ★★★★☆ | 中(按需分配) | 高(策略组合) |
3.2.1 物理隔离实战要点
- 存储层:每个租户独立 Elasticsearch 索引或 ClickHouse 表,通过 OTel Collector 的
exporters配置动态路由。 - Collector 层:使用
groupbyattrs处理器按tenant.id分发到不同 exporter。 - 查询层:每个租户独立 Grafana 数据源,避免跨租户数据泄露。
# OTel Collector 物理隔离配置示例(按租户分发到不同 ES 集群)
processors:
groupbyattrs:
keys:
- tenant.id
exporters:
elasticsearch/tenant-a:
endpoints: ["https://es-tenant-a:9200"]
index: "traces-tenant-a"
elasticsearch/tenant-b:
endpoints: ["https://es-tenant-b:9200"]
index: "traces-tenant-b"
service:
pipelines:
traces:
processors: [groupbyattrs]
exporters: [elasticsearch/tenant-a, elasticsearch/tenant-b]
3.2.2 逻辑隔离实战要点
- 数据打标:在 OTel SDK 端通过
Resource注入tenant.id,确保所有 Span 携带租户标识。 - 查询过滤:Grafana 或查询 API 强制附加
tenant.id过滤条件,防止越权访问。 - RBAC 集成:结合 OIDC/OAuth2,将用户租户映射到查询过滤器。
// Java OTel SDK 注入租户 ID
Resource resource = Resource.getDefault()
.merge(Resource.create(Attributes.of(
AttributeKey.stringKey("tenant.id"), "tenant-a",
AttributeKey.stringKey("environment"), "production"
)));
OpenTelemetry openTelemetry = OpenTelemetrySdk.builder()
.setResource(resource)
.build();
逻辑隔离风险提示:逻辑隔离依赖标签一致性与查询层严格过滤。若 SDK 端漏打
tenant.id,或查询层未强制过滤,会导致数据交叉泄露。建议在 Collector 端使用 filter 处理器做二次校验。
3.3 隔离粒度选择:从粗到细的决策树
隔离粒度决定了“隔什么”和“隔多细”。在 OTel 链路追踪中,常见粒度层级如下:
| 粒度层级 | 隔离对象 | 典型场景 | 实现成本 |
|---|---|---|---|
| 服务级 | 按 service.name 隔离 | 微服务内部不同团队 | 低 |
| 命名空间级 | 按 service.namespace 隔离 | K8s 多命名空间 | 低 |
| 租户级 | 按 tenant.id 隔离 | SaaS 多客户 | 中 |
| 链路级 | 按 trace_id + tenant.id 组合隔离 | 精细化权限控制 | 高 |
| Span 级 | 按 span 属性细粒度过滤 | 合规审计、敏感数据脱敏 | 高 |
3.4 隔离策略选择矩阵
综合多租户模型、数据隔离策略与隔离粒度,以下矩阵帮助你在实际项目中快速决策:
| 场景 | 推荐模型 | 推荐策略 | 推荐粒度 | 关键考量 |
|---|---|---|---|---|
| 内部开发团队(< 5 个) | 共享实例 | 逻辑隔离 | 服务级 | 快速迭代,低成本 |
| 多业务线共享平台 | 共享实例 | 逻辑隔离 | 命名空间级 | 标签治理,RBAC |
| SaaS 多租户(非金融) | 共享实例 | 逻辑隔离 | 租户级 | tenant.id 强制注入 |
| 金融/医疗合规场景 | 独立实例 | 物理隔离 | 租户级 | 审计、数据主权 |
| 大型企业分级管理 | 混合模型 | 混合隔离 | 按需选择 | 核心业务物理隔离 |
核心结论:在 OTel 链路追踪实践中,共享实例 + 逻辑隔离 + 租户级粒度 是 80% 场景的最优解。仅在强合规或性能隔离要求极高时,才考虑物理隔离或混合模型。隔离粒度越细,运维成本越高,需在安全与效率间取得平衡。