ElasticSearch教程FG041-ElasticSearch多租户架构实战
内容简介:本文档风哥主要介绍ElasticSearch多租户架构的设计与实现方法,包括索引隔离、文档隔离、集群隔离等方案,以及多租户管理和安全控制。通过学习本文,您将掌握如何构建一个安全、高效的ElasticSearch多租户架构。风哥教程参考ElasticSearch官方文档Security部分。
Part01-基础概念与理论知识
1.1 多租户架构概述
多租户架构是指在一个系统中同时为多个租户(客户)提供服务的架构模式。在ElasticSearch中,多租户架构可以通过以下方式实现:
- 索引隔离:为每个租户创建独立的索引
- 文档隔离:在同一个索引中通过字段区分不同租户的文档
- 集群隔离:为每个租户创建独立的ElasticSearch集群
1.2 多租户架构模式
多租户架构模式包括:
- 共享模式:多个租户共享同一个索引,通过字段区分
- 隔离模式:每个租户有独立的索引
- 混合模式:根据租户需求混合使用共享和隔离模式
1.3 多租户架构优势
多租户架构的优势包括:
- 资源共享:多个租户共享硬件资源,降低成本
- 管理简化:集中管理多个租户,简化运维
- 扩展性好:可以轻松添加新租户
- 隔离性强:租户之间相互隔离,提高安全性
- 灵活性高:可以根据租户需求进行定制
Part02-生产环境规划与建议
2.1 多租户架构设计
多租户架构设计建议:
- 根据租户规模选择隔离方案:大型租户使用独立索引,小型租户使用共享索引
- 合理规划索引命名:使用统一的命名规范,如 tenant-{tenant_id}-{index_name}
- 设置合理的分片策略:根据租户数据量设置合适的分片数
- 考虑数据生命周期:为不同租户设置不同的数据保留策略
- 监控与告警:为每个租户设置独立的监控和告警
2.2 资源隔离策略
资源隔离策略建议:
- 内存隔离:通过JVM堆大小限制每个租户的内存使用
- CPU隔离:通过线程池配置限制每个租户的CPU使用
- 磁盘隔离:通过索引配额限制每个租户的磁盘使用
- 网络隔离:通过网络带宽限制每个租户的网络使用
- 查询隔离:通过查询限制防止单个租户占用过多资源
2.3 安全与权限控制
安全与权限控制建议:
- 启用安全功能:启用ElasticSearch的安全功能,如X-Pack Security
- 创建租户用户:为每个租户创建独立的用户
- 设置角色权限:为每个租户设置合适的角色和权限
- 使用API密钥:为每个租户生成API密钥,用于身份验证
- 加密传输:启用SSL/TLS加密,保护数据传输安全
Part03-生产环境项目实施方案
3.1 索引隔离方案
索引隔离方案:
# 租户1
curl -X PUT “http://192.168.1.10:9200/tenant-1-users” -H “Content-Type: application/json” -d ‘{
“settings”: {
“number_of_shards”: 2,
“number_of_replicas”: 1
},
“mappings”: {
“properties”: {
“id”: {
“type”: “integer”
},
“name”: {
“type”: “text”
},
“age”: {
“type”: “integer”
}
}
}
}’
# 租户2
curl -X PUT “http://192.168.1.10:9200/tenant-2-users” -H “Content-Type: application/json” -d ‘{
“settings”: {
“number_of_shards”: 2,
“number_of_replicas”: 1
},
“mappings”: {
“properties”: {
“id”: {
“type”: “integer”
},
“name”: {
“type”: “text”
},
“age”: {
“type”: “integer”
}
}
}
}’
# 2. 为租户创建用户和角色
# 创建租户1用户
curl -X POST “http://192.168.1.10:9200/_security/user/tenant1” -H “Content-Type: application/json” -d ‘{
“password”: “tenant1_password”,
“roles”: [“tenant1_role”]
}’
# 创建租户1角色
curl -X POST “http://192.168.1.10:9200/_security/role/tenant1_role” -H “Content-Type: application/json” -d ‘{
“indices”: [
{
“names”: [“tenant-1-*”],
“privileges”: [“all”]
}
]
}’
# 创建租户2用户
curl -X POST “http://192.168.1.10:9200/_security/user/tenant2” -H “Content-Type: application/json” -d ‘{
“password”: “tenant2_password”,
“roles”: [“tenant2_role”]
}’
# 创建租户2角色
curl -X POST “http://192.168.1.10:9200/_security/role/tenant2_role” -H “Content-Type: application/json” -d ‘{
“indices”: [
{
“names”: [“tenant-2-*”],
“privileges”: [“all”]
}
]
}’
3.2 文档隔离方案
文档隔离方案:
curl -X PUT “http://192.168.1.10:9200/shared-users” -H “Content-Type: application/json” -d ‘{
“settings”: {
“number_of_shards”: 3,
“number_of_replicas”: 2
},
“mappings”: {
“properties”: {
“id”: {
“type”: “integer”
},
“name”: {
“type”: “text”
},
“age”: {
“type”: “integer”
},
“tenant_id”: {
“type”: “keyword”
}
}
}
}’
# 2. 插入不同租户的数据
# 租户1数据
curl -X POST “http://192.168.1.10:9200/shared-users/_doc/1” -H “Content-Type: application/json” -d ‘{
“id”: 1,
“name”: “张三”,
“age”: 25,
“tenant_id”: “tenant1”
}’
# 租户2数据
curl -X POST “http://192.168.1.10:9200/shared-users/_doc/2” -H “Content-Type: application/json” -d ‘{
“id”: 1,
“name”: “李四”,
“age”: 30,
“tenant_id”: “tenant2”
}’
# 3. 创建租户角色,限制只能访问自己的数据
# 创建租户1角色
curl -X POST “http://192.168.1.10:9200/_security/role/tenant1_role” -H “Content-Type: application/json” -d ‘{
“indices”: [
{
“names”: [“shared-users”],
“privileges”: [“read”, “write”],
“query”: “{\”term\”: {\”tenant_id\”: \”tenant1\”}}”
}
]
}’
# 创建租户2角色
curl -X POST “http://192.168.1.10:9200/_security/role/tenant2_role” -H “Content-Type: application/json” -d ‘{
“indices”: [
{
“names”: [“shared-users”],
“privileges”: [“read”, “write”],
“query”: “{\”term\”: {\”tenant_id\”: \”tenant2\”}}”
}
]
}’
3.3 集群隔离方案
集群隔离方案:
# 租户1集群
# 配置elasticsearch.yml
cluster.name: tenant1-cluster
node.name: tenant1-node-1
network.host: 192.168.1.10
http.port: 9200
transport.port: 9300
# 租户2集群
# 配置elasticsearch.yml
cluster.name: tenant2-cluster
node.name: tenant2-node-1
network.host: 192.168.1.11
http.port: 9200
transport.port: 9300
# 2. 启动每个集群
# 启动租户1集群
/es/app/elasticsearch-8.10.0/bin/elasticsearch -d
# 启动租户2集群
/es/app/elasticsearch-8.10.0/bin/elasticsearch -d
# 3. 验证集群状态
# 检查租户1集群
curl -X GET “http://192.168.1.10:9200/_cluster/health?pretty”
# 检查租户2集群
curl -X GET “http://192.168.1.11:9200/_cluster/health?pretty”
3.4 多租户管理
多租户管理:
vi /es/app/scripts/tenant_management.sh
#!/bin/bash
# tenant_management.sh
# from:www.itpux.com.qq113257174.wx:itpux-com
# web: `http://www.fgedu.net.cn`
# 创建租户
create_tenant() {
TENANT_ID=$1
TENANT_NAME=$2
echo “Creating tenant: $TENANT_NAME (ID: $TENANT_ID)”
# 创建租户索引
curl -X PUT “http://192.168.1.10:9200/tenant-${TENANT_ID}-users” -H “Content-Type: application/json” -d ‘{
“settings”: {
“number_of_shards”: 2,
“number_of_replicas”: 1
},
“mappings”: {
“properties”: {
“id”: {
“type”: “integer”
},
“name”: {
“type”: “text”
},
“age”: {
“type”: “integer”
}
}
}
}’
# 创建租户用户
curl -X POST “http://192.168.1.10:9200/_security/user/tenant${TENANT_ID}” -H “Content-Type: application/json” -d ‘{
“password”: “tenant${TENANT_ID}_password”,
“roles”: [“tenant${TENANT_ID}_role”]
}’
# 创建租户角色
curl -X POST “http://192.168.1.10:9200/_security/role/tenant${TENANT_ID}_role” -H “Content-Type: application/json” -d ‘{
“indices”: [
{
“names”: [“tenant-${TENANT_ID}-*”],
“privileges”: [“all”]
}
]
}’
echo “Tenant $TENANT_NAME created successfully”
}
# 删除租户
delete_tenant() {
TENANT_ID=$1
echo “Deleting tenant with ID: $TENANT_ID”
# 删除租户索引
curl -X DELETE “http://192.168.1.10:9200/tenant-${TENANT_ID}-*”
# 删除租户用户
curl -X DELETE “http://192.168.1.10:9200/_security/user/tenant${TENANT_ID}”
# 删除租户角色
curl -X DELETE “http://192.168.1.10:9200/_security/role/tenant${TENANT_ID}_role”
echo “Tenant with ID $TENANT_ID deleted successfully”
}
# 列出所有租户
list_tenants() {
echo “Listing all tenants…”
# 列出所有租户索引
curl -X GET “http://192.168.1.10:9200/_cat/indices/tenant-*?v”
# 列出所有租户用户
curl -X GET “http://192.168.1.10:9200/_security/user?pretty” | grep -E “tenant[0-9]+”
}
# 主函数
case $1 in
create)
create_tenant $2 $3
;;
delete)
delete_tenant $2
;;
list)
list_tenants
;;
*)
echo “Usage: $0 {create|delete|list} [tenant_id] [tenant_name]”
;;
esac
# 设置执行权限
chmod +x /es/app/scripts/tenant_management.sh
Part04-生产案例与实战讲解
4.1 索引隔离实战
索引隔离实战:
vi /es/app/scripts/tenant_management.sh
#!/bin/bash
# tenant_management.sh
# from:www.itpux.com.qq113257174.wx:itpux-com
# web: `http://www.fgedu.net.cn`
# 创建租户
create_tenant() {
TENANT_ID=$1
TENANT_NAME=$2
echo “Creating tenant: $TENANT_NAME (ID: $TENANT_ID)”
# 创建租户索引
curl -X PUT “http://192.168.1.10:9200/tenant-${TENANT_ID}-users” -H “Content-Type: application/json” -d ‘{
“settings”: {
“number_of_shards”: 2,
“number_of_replicas”: 1
},
“mappings”: {
“properties”: {
“id”: {
“type”: “integer”
},
“name”: {
“type”: “text”
},
“age”: {
“type”: “integer”
}
}
}
}’
# 创建租户用户
curl -X POST “http://192.168.1.10:9200/_security/user/tenant${TENANT_ID}” -H “Content-Type: application/json” -d ‘{
“password”: “tenant${TENANT_ID}_password”,
“roles”: [“tenant${TENANT_ID}_role”]
}’
# 创建租户角色
curl -X POST “http://192.168.1.10:9200/_security/role/tenant${TENANT_ID}_role” -H “Content-Type: application/json” -d ‘{
“indices”: [
{
“names”: [“tenant-${TENANT_ID}-*”],
“privileges”: [“all”]
}
]
}’
echo “Tenant $TENANT_NAME created successfully”
}
# 2. 创建租户
/es/app/scripts/tenant_management.sh create 1 “租户1”
/es/app/scripts/tenant_management.sh create 2 “租户2”
# 3. 验证租户创建
/es/app/scripts/tenant_management.sh list
# 4. 测试租户隔离
# 租户1登录
curl -u tenant1:tenant1_password -X GET “http://192.168.1.10:9200/tenant-1-users/_search?pretty”
# 租户2登录
curl -u tenant2:tenant2_password -X GET “http://192.168.1.10:9200/tenant-2-users/_search?pretty”
# 尝试访问其他租户的索引(应该失败)
curl -u tenant1:tenant1_password -X GET “http://192.168.1.10:9200/tenant-2-users/_search?pretty”
4.2 文档隔离实战
文档隔离实战:
curl -X PUT “http://192.168.1.10:9200/shared-users” -H “Content-Type: application/json” -d ‘{
“settings”: {
“number_of_shards”: 3,
“number_of_replicas”: 2
},
“mappings”: {
“properties”: {
“id”: {
“type”: “integer”
},
“name”: {
“type”: “text”
},
“age”: {
“type”: “integer”
},
“tenant_id”: {
“type”: “keyword”
}
}
}
}’
# 2. 插入测试数据
# 租户1数据
curl -X POST “http://192.168.1.10:9200/shared-users/_doc/1” -H “Content-Type: application/json” -d ‘{
“id”: 1,
“name”: “张三”,
“age”: 25,
“tenant_id”: “tenant1”
}’
# 租户2数据
curl -X POST “http://192.168.1.10:9200/shared-users/_doc/2” -H “Content-Type: application/json” -d ‘{
“id”: 1,
“name”: “李四”,
“age”: 30,
“tenant_id”: “tenant2”
}’
# 3. 创建租户角色
# 创建租户1角色
curl -X POST “http://192.168.1.10:9200/_security/role/tenant1_role” -H “Content-Type: application/json” -d ‘{
“indices”: [
{
“names”: [“shared-users”],
“privileges”: [“read”, “write”],
“query”: “{\”term\”: {\”tenant_id\”: \”tenant1\”}}”
}
]
}’
# 创建租户2角色
curl -X POST “http://192.168.1.10:9200/_security/role/tenant2_role” -H “Content-Type: application/json” -d ‘{
“indices”: [
{
“names”: [“shared-users”],
“privileges”: [“read”, “write”],
“query”: “{\”term\”: {\”tenant_id\”: \”tenant2\”}}”
}
]
}’
# 4. 创建租户用户
# 创建租户1用户
curl -X POST “http://192.168.1.10:9200/_security/user/tenant1” -H “Content-Type: application/json” -d ‘{
“password”: “tenant1_password”,
“roles”: [“tenant1_role”]
}’
# 创建租户2用户
curl -X POST “http://192.168.1.10:9200/_security/user/tenant2” -H “Content-Type: application/json” -d ‘{
“password”: “tenant2_password”,
“roles”: [“tenant2_role”]
}’
# 5. 测试文档隔离
# 租户1查询
curl -u tenant1:tenant1_password -X GET “http://192.168.1.10:9200/shared-users/_search?pretty”
# 租户2查询
curl -u tenant2:tenant2_password -X GET “http://192.168.1.10:9200/shared-users/_search?pretty”
4.3 集群隔离实战
集群隔离实战:
# 租户1集群:192.168.1.10
# 租户2集群:192.168.1.11
# 2. 配置租户1集群
vi /es/app/elasticsearch-8.10.0/config/elasticsearch.yml
cluster.name: tenant1-cluster
node.name: tenant1-node-1
network.host: 192.168.1.10
http.port: 9200
transport.port: 9300
discovery.seed_hosts: [“192.168.1.10”]
cluster.initial_master_nodes: [“tenant1-node-1”]
# 3. 配置租户2集群
vi /es/app/elasticsearch-8.10.0/config/elasticsearch.yml
cluster.name: tenant2-cluster
node.name: tenant2-node-1
network.host: 192.168.1.11
http.port: 9200
transport.port: 9300
discovery.seed_hosts: [“192.168.1.11”]
cluster.initial_master_nodes: [“tenant2-node-1”]
# 4. 启动集群
# 启动租户1集群
/es/app/elasticsearch-8.10.0/bin/elasticsearch -d
# 启动租户2集群
/es/app/elasticsearch-8.10.0/bin/elasticsearch -d
# 5. 验证集群状态
# 检查租户1集群
curl -X GET “http://192.168.1.10:9200/_cluster/health?pretty”
# 检查租户2集群
curl -X GET “http://192.168.1.11:9200/_cluster/health?pretty”
# 6. 为每个集群创建索引
# 租户1集群
curl -X PUT “http://192.168.1.10:9200/tenant1-users” -H “Content-Type: application/json” -d ‘{
“settings”: {
“number_of_shards”: 2,
“number_of_replicas”: 1
},
“mappings”: {
“properties”: {
“id”: {
“type”: “integer”
},
“name”: {
“type”: “text”
},
“age”: {
“type”: “integer”
}
}
}
}’
# 租户2集群
curl -X PUT “http://192.168.1.11:9200/tenant2-users” -H “Content-Type: application/json” -d ‘{
“settings”: {
“number_of_shards”: 2,
“number_of_replicas”: 1
},
“mappings”: {
“properties”: {
“id”: {
“type”: “integer”
},
“name”: {
“type”: “text”
},
“age”: {
“type”: “integer”
}
}
}
}’
4.4 多租户管理实战
多租户管理实战:
# 创建租户
/es/app/scripts/tenant_management.sh create 1 “租户1”
/es/app/scripts/tenant_management.sh create 2 “租户2”
/es/app/scripts/tenant_management.sh create 3 “租户3”
# 列出租户
/es/app/scripts/tenant_management.sh list
# 删除租户
/es/app/scripts/tenant_management.sh delete 3
# 2. 监控租户资源使用
# 查看租户索引大小
curl -X GET “http://192.168.1.10:9200/_cat/indices/tenant-*?v&s=pri.store.size:desc”
# 查看租户查询性能
curl -X GET “http://192.168.1.10:9200/_nodes/stats/indices/search?pretty”
# 3. 为租户设置资源限制
# 设置索引配额
curl -X PUT “http://192.168.1.10:9200/_cluster/settings” -H “Content-Type: application/json” -d ‘{
“persistent”: {
“cluster”: {
“indices”: {
“quota”: {
“enabled”: “true”,
“default”: “50gb”
}
}
}
}
}’
# 为特定租户设置配额
curl -X PUT “http://192.168.1.10:9200/tenant-1-*/_settings” -H “Content-Type: application/json” -d ‘{
“index”: {
“quota”: {
“size”: “100gb”
}
}
}’
Part05-风哥经验总结与分享
5.1 多租户架构最佳实践
- 根据租户规模选择隔离方案:大型租户使用独立索引或集群,小型租户使用共享索引
- 合理规划索引命名:使用统一的命名规范,便于管理
- 设置资源限制:为每个租户设置合理的资源限制,防止资源滥用
- 加强安全控制:启用安全功能,设置合适的角色和权限
- 监控与告警:为每个租户设置独立的监控和告警
- 自动化管理:使用脚本自动化租户管理,减少人工操作
5.2 常见问题与解决方案
- 资源竞争:设置资源限制,防止单个租户占用过多资源
- 性能下降:优化查询,合理设置分片策略,增加硬件资源
- 安全问题:加强安全控制,设置合适的角色和权限
- 管理复杂:使用脚本自动化租户管理,减少人工操作
- 数据隔离:确保租户之间数据严格隔离,防止数据泄露
- 扩展性:设计可扩展的架构,便于添加新租户
5.3 性能优化建议
- 分片策略优化:根据租户数据量设置合理的分片数
- 缓存优化:合理配置缓存,提高查询性能
- 查询优化:优化查询语句,避免全表扫描
- 硬件优化:使用高性能硬件,如SSD存储
- 网络优化:确保网络连接稳定,延迟低
- 监控优化:建立完善的监控体系,及时发现性能问题
更多视频教程www.fgedu.net.cn
学习交流加群风哥微信: itpux-com
学习交流加群风哥QQ113257174
风哥提示:多租户架构是ElasticSearch在SaaS场景中的重要应用,需要合理设计和管理
更多学习教程公众号风哥教程itpux_com
from ElasticSearch视频:www.itpux.com
本文由风哥教程整理发布,仅用于学习测试使用,转载注明出处:http://www.fgedu.net.cn/10327.html
