Istio安全与故障排查全解析
1. 授权管理
在完成用户身份验证后,并非所有用户都被允许访问应用的所有部分,这就需要进行授权管理。基于角色的访问控制(RBAC)常被用于限制用户只能使用适用于他们的功能。Istio在Envoy代理中运行RBAC引擎,代理从Pilot获取适用的RBAC策略,并将请求中的JWT与配置的授权策略进行比较,从而决定是否允许该请求。
默认情况下,Istio禁用基于角色的访问控制。要启用它,可应用以下配置:
apiVersion: "rbac.istio.io/v1alpha1"
kind: ClusterRbacConfig
metadata:
name: default
spec:
mode: 'ON_WITH_INCLUSION'
inclusion:
namespaces: ["default"]
此配置为“default”命名空间启用了RBAC控制。
ClusterRbacConfig
是一个单例集群范围的对象,名为
default
。
mode
还有其他值可用于微调RBAC:
-
OFF
:禁用Istio授权。
-
ON
:为网格中的所有服务启用Istio授权。
-
ON_WITH_INCLUSION
:仅为
inclusion
字段中指定的服务和命名空间启用Istio授权。
-
ON_WITH_EXCLUSION
:为网格中的所有服务启用Istio授权,但排除
exclusion
字段中指定的服务和命名空间。
启用RBAC后,使用
curl
命令访问服务可能会失败并返回403响应:
$ curl --header "Authorization: Bearer $TOKEN" -v http://10.152.183.230/
< HTTP/1.1 403 Forbidden
< content-length: 19
< content-type: text/plain
RBAC: access denied
接下来需要定义角色和权限。权限可以在服务级别定义,也可以针对路径、HTTP方法和请求头进行微调,这通过
ServiceRole
配置来实现。例如,定义一个
http-viewer
角色用于访问
webservice
:
---
apiVersion: "rbac.istio.io/v1alpha1"
kind: ServiceRole
metadata:
name: http-viewer
spec:
rules:
- services: ["webservice"]
methods: ["GET"]
还可以定义一个用于执行更新操作的
http-update-webservice
角色:
---
apiVersion: "rbac.istio.io/v1alpha1"
kind: ServiceRole
metadata:
name: http-update-webservice
spec:
rules:
- services: ["webservice"]
methods: ["POST"]
定义好角色后,需要将其分配给用户。可以通过
ServiceRoleBinding
来实现,例如将
http-viewer
角色分配给所有用户:
---
apiVersion: "rbac.istio.io/v1alpha1"
kind: ServiceRoleBinding
metadata:
name: bind-http-viewer
spec:
subjects:
- user: "*"
roleRef:
kind: ServiceRole
name: "http-viewer"
也可以根据用户令牌的属性验证用户主体并分配相应的角色,例如将
http-update-webservice
角色分配给具有
webservice
范围JWT的请求:
---
apiVersion: "rbac.istio.io/v1alpha1"
kind: ServiceRoleBinding
metadata:
name: bind-http-update
spec:
subjects:
- properties:
request.auth.claims[scope]: "webservice"
roleRef:
kind: ServiceRole
name: "http-update-webservice"
应用上述
ServiceRole
和
ServiceRoleBinding
配置后,再次使用
curl
命令应该能按预期工作。
2. 规则引擎
除了身份验证和授权策略,策略还可用于实施应用规则,这对运维团队很有用,他们可以创建规则来管理资源利用率或控制应用的黑白名单等。由于这些需求基于运行时行为,具有多样性,因此使用规则引擎来实现这些不断变化的需求是个好主意。Istio支持使用Mixer组件进行规则验证,Mixer由三部分组成:
-
Handler
:定义适配器配置。
-
Instance
:定义请求需要捕获的属性。
-
Rule
:将处理程序与可以发送所需数据的实例关联起来。
Envoy代理将请求发送到Istio Pilot,Pilot调用Mixer,Mixer根据
Instance
配置捕获数据并发送到
Handler
。
Handler
可以将数据捕获到外部系统,也可以对收到的请求进行布尔检查,Envoy代理根据检查响应允许或拒绝请求。
要启用规则检查,可使用以下命令:
$ kubectl get cm istio -n istio-system -o yaml | sed -e "s/ disablePolicyChecks: true/ disablePolicyChecks: false/" | kubectl apply -f - configmap/istio configured
下面是一个配置白名单规则的示例,只允许前端服务访问
webapp
:
---
apiVersion: config.istio.io/v1alpha2
kind: handler
metadata:
name: whitelist
spec:
compiledAdapter: listchecker
params:
overrides: ["frontend"]
blacklist: true
---
apiVersion: config.istio.io/v1alpha2
kind: instance
metadata:
name: appsource
spec:
compiledTemplate: listentry
params:
value: source.labels["app"]
---
apiVersion: config.istio.io/v1alpha2
kind: rule
metadata:
name: checksrc
spec:
match: destination.labels["app"] == "webapp"
actions:
- handler: whitelist
instances: [ appsource ]
执行
curl
命令访问服务可能会失败:
$curl -v http://10.152.183.230/
> GET / HTTP/1.1
> Host: 10.152.183.146
> User-Agent: curl/7.58.0
> Accept: */*
>
* Empty reply from server
* Connection #0 to host 10.152.183.
curl: (52) Empty reply from server
但如果对前端服务执行
curl
命令,将得到预期响应。通过更改
Handler
的
blacklist
属性,可以将白名单切换为黑名单。Istio还提供了一些处理程序,可用于执行各种检查,如配额管理、简单拒绝等。
3. 故障排查工具
Istio服务网格中的故障排查非常复杂,因为有许多组件协同工作,每个系统都有其细微差别。以下是一些可用于排查服务网格问题的工具。
3.1 Configmaps
Istio的许多功能由相应的功能标志驱动,这些配置标志是确定功能如何配置的首要位置,能回答一系列问题,如Envoy代理使用的配置、网关的工作方式、Istio的分布式跟踪是否启用以及配置了哪个跟踪提供程序等。
Istio由两个Kubernetes Configmaps驱动:
-
istio
:定义Istio Pilot、Mixer、Tracing、Prometheus、Grafana等的配置,每个组件的配置选项都以组件名称为前缀。
-
istio-sidecar-injector
:定义Istio边车的配置,包括Pilot、Kubernetes API服务器的位置等。
可以使用以下命令获取这些Configmaps:
$kubectl -n istio-system get cm istio -o jsonpath="{@.data.mesh}"
disablePolicyChecks: false
enableTracing: true
accessLogFile: "/dev/stdout"
#REMOVED for BREVITY
$kubectl -n istio-system get cm istio-sidecar-injector -o jsonpath="{@.data.config}"
policy: enabled
alwaysInjectSelector:
[]
template: |-
rewriteAppHTTPProbe: {{ valueOrDefault .Values.sidecarInjector Webhook.rewriteAppHTTPProbe false }}
{{- if or (not .Values.istio_cni.enabled) .Values.global.proxy.enableCoreDump }}
initContainers:
#REMOVED for BREVITY
还可以使用以下命令列出所有自动注入Istio边车的命名空间:
$kubectl get namespace -L istio-injection
NAME STATUS AGE ISTIO-INJECTION
default Active 221d enabled
istio-system Active 60d disabled
kube-node-lease Active 75d
kube-public Active 221d
kube-system Active 221d
3.2 Proxy
Istio的大部分功能通过Envoy代理实现,代理与Istio Pilot连接以获取最新配置。因此,了解Envoy代理是否与Pilot中的最新策略同步非常重要。可以使用
istioctl proxy-status
命令获取所有代理的状态:
$ istioctl proxy-status
PROXY CDS LDS EDS RDS PILOT VERSION
istio-ingress-6458b8c98f-7ks48.istio-system SYNCED SYNCED SYNCED NOT SENT istio-pilot-75bdf98789-n2kqh 1.1.2
istio-ingressgateway-7d6874b48f-qxhn5.istio-system SYNCED SYNCED SYNCED SYNCED istio-pilot-75bdf98789-n2kqh 1.1.2
productpage-v1-6c886ff494-hm7zk.default SYNCED SYNCED SYNCED STALE istio-pilot-75bdf98789-n2kqh 1.1.2
ratings-v1-5d9ff497bb-gslng.default SYNCED SYNCED SYNCED SYNCED istio-pilot-75bdf98789-n2kqh 1.1.2
webservice-v1-55d4c455db-zjj2m.default SYNCED SYNCED SYNCED SYNCED istio-pilot-75bdf98789-n2kqh 1.1.2
webservice-v2-686bbb668-99j76.default SYNCED SYNCED SYNCED SYNCED istio-pilot-75bdf98789-tfdvh 1.1.2
webservice-v3-7b9b5fdfd6-4r52s.default SYNCED SYNCED SYNCED SYNCED istio-pilot-75bdf98789-n2kqh 1
所有运行的代理将处于以下状态之一:
-
SYNCED
:表示边车已更新所有更改。
-
STALE
:表示有更改,但边车尚未获取这些更改。
-
NOT SENT
:表示没有更改。
如果代理未在列表中,则表示它未连接到Istio Pilot。可以使用以下命令查找代理配置:
$ istioctl proxy-config bootstrap -n istio-egressgateway-9b7866bf5-8p5rt.istio-system
{
"bootstrap": {
"node": {
"id": "router~172.30.86.14~ istio-egressgateway-9b7866bf5-8p5rt -system~istio-system.svc.cluster.local",
"cluster": "istio-ingressgateway",
"metadata": {
"POD_NAME": " istio-egressgateway-9b7866bf5-8p5rt ",
"istio": "sidecar"
},
"buildVersion": "0/1.8.0 //RELEASE"
},
// REMOVED for BREVITY
}
}
最后,可以通过查看代理日志来了解其行为:
$kubectl logs pod/frontend-deployment-78d98b75f4-rwkbm istio-proxy
[2019-09-15T20:17:00.310Z] "GET / HTTP/2" 204 - 154 0 226 100 "10.0.35.28"
"" "cc21d9b0-cf5c-432b-8c7e-98aeb7988cd2" "" "tcp://10.0.2.1:8080"
[2019-09-15T20:17:01.102Z] "GET / HTTP/2" 204 - 154 0 226 100 "10.0.35.28"
"" "cc21d9b0-tfdvh-432b-n2kqh-75bdf98789" "" "tcp://10.0.2.1:8080"
3.3 Routes
流量路由是Istio的重要功能之一。当虚拟服务无法正常工作,相关的目标规则也可能失败时,可以通过确定Istio边车监听的端口来开始排查流量路由问题。
使用以下命令总结代理监听的端口:
$ istioctl proxy-config listeners istio-ingressgateway-75ddf64567-jtl68.istio-system
ADDRESS PORT TYPE
0.0.0.0 15090 HTTP
要获取代理针对特定端口的流量设置的详细信息,可使用以下命令:
$ istioctl proxy-config listeners istio-egressgateway-9b7866bf5-8p5rt.istio-system -o json --address 0.0.0.0 --port 15090
[
{
"address": {
"socketAddress": {
"address": "0.0.0.0",
"portValue": 15090
}
},
// REMOVED for BREVITY
}
]
该命令会显示用于指定端口的路由名称。可以使用以下命令查找该路由解析的主机:
$ istioctl proxy-config routes frontend-v1-6549877cc8-67cc8 --name 8080 -o json
[
{
"name": "8080",
"virtualHosts": [
{
"name": "webservice.default.svc.cluster.local:8080",
"domains": [
"webservice.default.svc.cluster.local",
"webservice.default.svc.cluster.local:8080",
"webservice",
"webservice:8080",
"webservice.default.svc.cluster",
"webservice.default.svc.cluster:8080",
// REMOVED for BREVITY
],
"routes": [
{
"match": {
"prefix": "/"
},
"route": {
"cluster": "outbound|8080||web service.default.svc.cluster.local",
"timeout": "0.000s"
},
// REMOVED for BREVITY
}
]
}
]
}
]
可以看到不同的Web服务域和IP地址解析为出站地址。可以使用以下命令确定解析的出站地址配置的集群位置:
$ istioctl proxy-config cluster frontend-v1-6549877cc8-67cc8 --fqdn webservice.default.svc.cluster.local -o json
[
{
"name": "outbound|8080||webservice.default.svc.cluster.local",
"type": "EDS",
"edsClusterConfig": {
"edsConfig": {
"ads": {}
},
"serviceName": "outbound|8080||webservice.default.svc.cluster.local"
},
"connectTimeout": "1.000s",
"circuitBreakers": {
"thresholds": [
{}
]
}
}
]
最后,可以验证集群位置的端点:
$ istioctl proxy-config endpoints frontend-v1-6549877cc8-67cc8 --cluster "outbound|8080||webservice.default.svc.cluster.local"
ENDPOINT STATUS OUTLIER CHECK CLUSTER
172.17.0.17:8080 HEALTHY OK outbound|8080||webservice.default.svc.cluster.local
172.17.0.18:8080 HEALTHY OK outbound|8080||webservice.default.svc.cluster.local
172.17.0.5:8080 HEALTHY OK outbound|8080||webservice.default.svc.cluster.local
目标规则还用于在客户端配置相互TLS身份验证。但有时目标规则可能不起作用,握手会失败并返回503错误代码。在这种情况下,必须检查目标规则是否违反现有配置:
$ istioctl authn tls-check istio-ingressgateway-75ddf64567-jtl68.istio-system
HOST:PORT STATUS SERVER CLIENT AUTHN POLICY DESTINATION RULE
grafana.istio-system.svc.cluster.local:3000 OK HTTP HTTP grafana-ports-mtls-disabled/istio-system -
istio-citadel.istio-system.svc.cluster.local:8060 OK HTTP/mTLS HTTP default/ -
istio-citadel.istio-system.svc.cluster.local:15014 OK HTTP/mTLS HTTP default/ -
综上所述,Istio的授权管理、规则引擎和故障排查工具对于保障服务的安全性、稳定性和可靠性至关重要。通过合理配置和使用这些功能,可以更好地管理和维护Istio服务网格。
Istio安全与故障排查全解析(续)
4. 授权管理总结
授权管理是Istio安全体系中的重要环节,基于角色的访问控制(RBAC)为不同用户分配不同的访问权限,确保系统的安全性和数据的保密性。以下是授权管理的关键步骤总结:
1.
启用RBAC
:通过
ClusterRbacConfig
配置启用RBAC,并选择合适的
mode
。
yaml
apiVersion: "rbac.istio.io/v1alpha1"
kind: ClusterRbacConfig
metadata:
name: default
spec:
mode: 'ON_WITH_INCLUSION'
inclusion:
namespaces: ["default"]
2.
定义角色
:使用
ServiceRole
配置定义不同的角色,如
http-viewer
和
http-update-webservice
。
yaml
---
apiVersion: "rbac.istio.io/v1alpha1"
kind: ServiceRole
metadata:
name: http-viewer
spec:
rules:
- services: ["webservice"]
methods: ["GET"]
3.
分配角色
:使用
ServiceRoleBinding
将角色分配给用户或用户组。
yaml
---
apiVersion: "rbac.istio.io/v1alpha1"
kind: ServiceRoleBinding
metadata:
name: bind-http-viewer
spec:
subjects:
- user: "*"
roleRef:
kind: ServiceRole
name: "http-viewer"
5. 规则引擎总结
规则引擎为运维团队提供了强大的工具,用于管理资源利用率和控制应用的黑白名单等。Istio的Mixer组件是规则引擎的核心,其工作流程如下:
graph LR
A[Envoy代理] --> B[Istio Pilot]
B --> C[Mixer]
C --> D[Instance(捕获数据)]
D --> E[Handler(处理数据)]
E --> F{布尔检查}
F -->|允许| G[Envoy代理允许请求]
F -->|拒绝| H[Envoy代理拒绝请求]
关键步骤如下:
1.
启用规则检查
:通过修改
istio
Configmap中的
disablePolicyChecks
标志来启用规则检查。
bash
$ kubectl get cm istio -n istio-system -o yaml | sed -e "s/ disablePolicyChecks: true/ disablePolicyChecks: false/" | kubectl apply -f - configmap/istio configured
2.
配置规则
:使用
handler
、
instance
和
rule
配置规则,如白名单规则。
yaml
---
apiVersion: config.istio.io/v1alpha2
kind: handler
metadata:
name: whitelist
spec:
compiledAdapter: listchecker
params:
overrides: ["frontend"]
blacklist: true
---
apiVersion: config.istio.io/v1alpha2
kind: instance
metadata:
name: appsource
spec:
compiledTemplate: listentry
params:
value: source.labels["app"]
---
apiVersion: config.istio.io/v1alpha2
kind: rule
metadata:
name: checksrc
spec:
match: destination.labels["app"] == "webapp"
actions:
- handler: whitelist
instances: [ appsource ]
6. 故障排查总结
故障排查是Istio运维中的重要工作,以下是不同方面的故障排查总结:
6.1 Configmaps排查
| Configmap名称 | 作用 | 获取命令 |
|---|---|---|
istio
| 定义Istio多个组件的配置 |
$kubectl -n istio-system get cm istio -o jsonpath="{@.data.mesh}"
|
istio-sidecar-injector
| 定义Istio边车的配置 |
$kubectl -n istio-system get cm istio-sidecar-injector -o jsonpath="{@.data.config}"
|
6.2 Proxy排查
-
检查代理状态
:使用
istioctl proxy-status命令检查代理状态。
bash $ istioctl proxy-status
代理状态有SYNCED(已更新)、STALE(有更改未更新)和NOT SENT(无更改)。 -
查看代理配置
:使用
istioctl proxy-config bootstrap命令查看代理配置。
bash $ istioctl proxy-config bootstrap -n istio-egressgateway-9b7866bf5-8p5rt.istio-system -
查看代理日志
:使用
kubectl logs命令查看代理日志。
bash $kubectl logs pod/frontend-deployment-78d98b75f4-rwkbm istio-proxy
6.3 Routes排查
-
确定监听端口
:使用
istioctl proxy-config listeners命令确定代理监听的端口。
bash $ istioctl proxy-config listeners istio-ingressgateway-75ddf64567-jtl68.istio-system -
获取端口详细配置
:使用
istioctl proxy-config listeners命令获取特定端口的详细配置。
bash $ istioctl proxy-config listeners istio-egressgateway-9b7866bf5-8p5rt.istio-system -o json --address 0.0.0.0 --port 15090 -
查找路由解析的主机
:使用
istioctl proxy-config routes命令查找路由解析的主机。
bash $ istioctl proxy-config routes frontend-v1-6549877cc8-67cc8 --name 8080 -o json -
确定集群位置
:使用
istioctl proxy-config cluster命令确定解析的出站地址配置的集群位置。
bash $ istioctl proxy-config cluster frontend-v1-6549877cc8-67cc8 --fqdn webservice.default.svc.cluster.local -o json -
验证端点
:使用
istioctl proxy-config endpoints命令验证集群位置的端点。
bash $ istioctl proxy-config endpoints frontend-v1-6549877cc8-67cc8 --cluster "outbound|8080||webservice.default.svc.cluster.local" -
检查目标规则
:使用
istioctl authn tls-check命令检查目标规则是否违反现有配置。
bash $ istioctl authn tls-check istio-ingressgateway-75ddf64567-jtl68.istio-system
7. 总结与建议
Istio提供了丰富的功能来保障服务的安全性、稳定性和可靠性,但同时也带来了一定的复杂性。在实际应用中,建议按照以下步骤进行操作:
1.
规划授权策略
:根据业务需求,合理规划RBAC策略,定义不同的角色和权限,并将其分配给合适的用户或用户组。
2.
配置规则引擎
:根据运维需求,配置规则引擎,如黑白名单规则、配额管理规则等,确保系统资源的合理利用。
3.
建立故障排查机制
:熟悉各种故障排查工具和命令,建立完善的故障排查机制,以便在出现问题时能够快速定位和解决问题。
通过以上步骤,可以更好地管理和维护Istio服务网格,提高服务的质量和可靠性。
超级会员免费看
1043

被折叠的 条评论
为什么被折叠?



