什么是服务网络?
服务网络(Service Network) 是一个核心概念,用于定义集群内部服务间通信的抽象层。它通过虚拟 IP 地址(ClusterIP)和 DNS 名称,为 Pod 提供稳定的访问端点,屏蔽后端 Pod 的动态变化(如扩缩容、重启等)。
服务网格的诞生将程序开发的网络功能和程序本身解耦,网络功能下沉 到基础架构,由服务网格实现服务之间的负载均衡等功能,并且除网络功能 外,还提供了其他更高级的功能,比如全链路加密、监控、链路追踪等。
服务网络的功能:
负载均衡:运行环境中的微服务实例通常处于动态变化状态,而且 经常可能出现个别实例不能正常提供服务、处理能力减弱、卡顿等 现象。但由于所有请求对服务网格来说是可见的,因此可以通过提 供高级负载均衡算法来实现更加智能、高效的流量分发,以降低延 时,提高可靠性。 ·
服务发现:以微服务模式运行的应用变更非常频繁,应用实例的频 繁增加和减少带来的问题是,如何精确地发现新增实例以及避免将 请求发送给已不存在的实例而变得更加复杂。服务网格可以提供简 单、统一、平台无关的多种服务发现机制,如基于DNS、键-值对 (key-value pair)存储的服务发现机制。 ·
熔断:在动态环境中,服务实例中断或不健康导致的服务中断可能 会经常发生,这就要求应用或者其他工具具有快速监测并从负载均 衡池中移除不提供服务实例的能力,这种能力也称熔断,以此使得 应用无须消耗更多不必要的资源不断地尝试,而是快速失败或者降 级,从而避免一些潜在的关联性错误,而服务网格可以很容易地实 现基于请求和连接级别的熔断机制。
动态路由:随着服务提供商以提供高稳定性、高可用性及高SLA服务 为主要目标,出现的各种应用部署策略都尽可能达到无服务中断部 署 , 以 此 避 免 变 更 而 导 致 服 务 的 中 断 和 稳 定 性 降 低 , 例 如 Blue/Green部署、Canary部署,但是实现这些高级部署策略通常非 常 困 难 。
安全通信:无论何时,安全在整个公司、业务系统中都占据着举足 轻重的位置,也是非常难以实现和控制的部分。而在微服务环境 中,不同的服务实例间的通信变得更加复杂,那么如何保证这些通 信是在安全、授权的情况下进行的就非常重要。通过将安全机制 (如TLS加解密和授权)实现在服务网格上,不仅可以避免在不同应 用上的重复实现,而且很容易在整个基础设施层更新安全机制,甚 至无须对应用做任何操作。
重试和最后期限:服务网格的重试功能可以避免将其嵌入业务代码 中,同时最后期限使得应用允许一个请求的最长生命周期,而不是 无休止地重试。
服务网格产品
Linkerd:是Buoyant公司在2016年率先开源的高性能网络代理程 序,它的出现标志着服务网格时代的开始。 ·
Envoy:同Linkerd一样,Envoy也是一款高性能的网络代理程序,为 云原生应用而设计。 ·
Istio:Istio受Google、IBM、Lyft及RedHat等公司的大力支持和推 广,于2017年5月发布,底层为Envoy。
Istio的基本概念:
Istio有助于降低应用部署的复杂性,并减轻开发团队的压力。Istio是 一个完全开源的服务网格产品,可以透明地分层到现有的分布式应用程序 上。同时,Istio拥有可以集成任何日志、遥测和策略系统的API接口。Istio 的多样化能够高效地运行于分布式微服务架构中,并提供保护、链接和监控 服务的统一方法。
Istio提供了一种简单的方式来为已部署的服务建立网络,该网络具有负 载均衡、服务间认证、监控等功能。
Istio的架构:
数据平面:由一组sidecar方式部署的智能代理组成,这些代理可以调节和控制微服务及mixer之间的所有的网络通信,还可以收集和报告网格流量的遥测数据,在k8s中和应用的容器处于同一个pod
控制平面:负责管理和配置代理来路由流量,由管理员创建的istio资源会解析成相关的配置下发到数据平面
服务网络的核心组成
组件 |
作用 |
---|---|
Service |
为一组 Pod 提供统一的访问入口(虚拟 IP + 端口) |
Endpoints |
动态维护 Service 对应的真实 Pod IP 列表 |
kube-proxy |
在每个节点上维护网络规则(iptables/IPVS),实现流量转发 |
CoreDNS |
提供集群内服务域名解析(如 |
Istio的核心资源
VirtualService
Istio 最 为 重 要 的 一 个 概 念 就 是 VirtualService ( 虚 拟 服 务 ) , 和 Kubernetes 的 Service 类 似 , 但 是 两 种 并 不 是 对 等 的 资 源 类 型 。 VirtualService基于Istio和对应平台提供的基本连通性和服务发现能力,将 请求路由到对应的目标。每一个VirtualService包含一组路由规则,Istio将 每个请求根据路由匹配到指定的目标地址。
和Kubernetes的Service不同的是,Kubernetes的Service只提供了最简 单的服务发现和负载均衡的能力,如果想要实现更加细粒度的流量分发,比 如灰度、蓝绿等流量管理,Kubernetes的Service显得比较吃力或者无法实 现,而VirtualService在流量管理方面有着比较好的灵活性和有效性,可以 在代码零侵入的情况下实现更加丰富的流量管理,比如灰度等。
DestinationRule
Istio另一个比较重要的资源是DestinationRule(目标规则),初学者 第一次接触Istio时,往往无法区分VirtualService和DestinationRule,在 实际使用时很容易混淆两者的概念和用途。
我 们 可 以 将 VirtualService 理 解 为 Kubernetes Service 层 面 , DestinationRule理解为Service后端真实的目标地址,即VirtualService用 于Service层面的路由管控,DestinationRule用于对后端真实的服务再做进 一步的划分。比如存在一个Service名为paycenter,指向后端多个paycenter 的Pod(该Pod可能是不同的Deployment创建的),而DestinationRule可以对 后端的多个Pod区分新旧版本,划分成不同的subnet,之后VirtualService可 以针对不同的版本进行流量管控。
Gateway
Istio同样支持网关功能,可以使用Gateway在网格最外层接收HTTP/TCP 流量,并将流量转发到网格内的某个服务。
在安装Istio时,可以在istio-system命名空间下安装ingressgateway的 Pod,用来充当Ingress Gateway。其中Ingress Gateway为入口网关,可以将 网格内的服务“暴露”出去,一般和VirtualService配置使用,并配置一个 可以被外部服务访问的域名,从而外部服务可以通过该域名访问网格内的服 务。
安装Istio
下载istio
GCS browser: istio-release 注意与k8s版本要对应
[root@k8s-master ~]# tar -xvf istio-1.6.5-linux-amd64.tar.gz
[root@k8s-master istio-1.6.5]# cd bin/
[root@k8s-master bin]# ll
total 105216
-rwxr-xr-x 1 root root 107739671 Jul 8 2020 istioctl
[root@k8s-master bin]# export PATH=$PWD:$PATH
[root@k8s-master tools]# yum install bash-completion -y
[root@k8s-master tools]# source /usr/share/bash-completion/bash_completion
[root@k8s-master tools]# source istioctl.bash
[root@k8s-master tools]# istioctl
analyze convert-ingress deregister install manifest profile proxy-status upgrade verify-install
authz dashboard experimental kube-inject operator proxy-config register validate version
安装istio
[root@k8s-master tools]# istioctl manifest apply --set profile=demo
WARNING: Istio control planes installed: 1.21.0.
WARNING: An older installed version of Istio has been detected. Running this command will overwrite it.
This will install the Istio 1.15.2 demo profile with ["Istio core" "Istiod" "Ingress gateways" "Egress gateways"] components into the cluster. Proceed? (y/N) y
✔ Istio core installed
✔ Istiod installed
✔ Ingress gateways installed
✔ Egress gateways installed
✔ Installation complete Making this installation the default for injection and validation.
Thank you for installing Istio 1.15. Please take a few minutes to tell us about your install/upgrade experience! https://forms.gle/SWHFBmwJspusK1hv6
确保kubernetes pod已经部署,并且状态为running:
[root@k8s-master tools]# kubectl get pod,svc -n istio-system
NAME READY STATUS RESTARTS AGE
pod/istio-egressgateway-6c879bb799-zhwz8 1/1 Running 0 5m54s
pod/istio-ingressgateway-5d88dc9989-ktlxp 1/1 Running 0 5m54s
pod/istiod-65ffd6796d-vz24q 1/1 Running 0 6m44s
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/istio-egressgateway ClusterIP 10.96.157.243 <none> 80/TCP,443/TCP 5m53s
service/istio-ingressgateway LoadBalancer 10.96.2.197 <pending> 15021:30612/TCP,80:30004/TCP,443:31950/TCP,31400:30724/TCP,15443:32317/TCP 5m53s
service/istiod ClusterIP 10.96.32.165 <none> 15010/TCP,15012/TCP,443/TCP,15014/TCP,853/TCP 18m
Bookinfo示例
启动应用服务
进入istio安装目录之后,istio默认自动注入Sider,为default命名空间打上标签istio-injection=enabled:
[root@k8s-master kube]# kubectl label namespace default istio-injection=enabled
namespace/default labeled
使用kubectl部署应用:
kubectl apply -f samples/bookinfo/platform/kube/bookinfo.yaml
查看所有的服务和pod都正常启动:
[root@k8s-master kube]# kubectl get pod
NAME READY STATUS RESTARTS AGE
details-v1-6758dd9d8d-qd6mk 2/2 Running 0 9m9s
productpage-v1-797d845774-jsq62 2/2 Running 0 9m3s
reviews-v1-74fb8fdbd8-9dzm5 2/2 Running 0 66m
reviews-v2-58d564d4db-67646 2/2 Running 0 66m
reviews-v3-55545c459b-bmphm 2/2 Running 0 66m
[root@k8s-master kube]# kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
details ClusterIP 10.96.204.122 <none> 9080/TCP 92m
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 26d
productpage ClusterIP 10.96.36.61 <none> 9080/TCP 92m
ratings ClusterIP 10.96.68.254 <none> 9080/TCP 92m
reviews ClusterIP 10.96.204.34 <none> 9080/TCP 92m
要确认bookinfo应用是否正在运行,在某个pod中用curl命令对应发送请求:
[root@k8s-master kube]# kubectl exec -it $(kubectl get pod -l app=ratings -o jsonpath='{.items[0].metadata.name}') -c ratings -- curl productpage:9080/productpage | grep -o "<title>.*</title>"
<title>Simple Bookstore App</title>
确定Ingress 的IP
为应用程序定义Ingress网关:
[root@k8s-master networking]# kubectl apply -f samples/bookinfo/networking/bookinfo-gateway.yaml
gateway.networking.istio.io/bookinfo-gateway created
virtualservice.networking.istio.io/bookinfo created
[root@k8s-master networking]# kubectl get gateway
NAME AGE
bookinfo-gateway 8s
设置访问网关的ingress_host和ingress_port变量。确认并设置
#设置 ingress 端口
export INGRESS_PORT=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.spec.ports[?(@.name=="http2")].nodePort}')
export SECURE_INGRESS_PORT=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.spec.ports[?(@.name=="https")].nodePort}')
#设置 ingress IP
export INGRESS_HOST=$(kubectl get po -l istio=ingressgateway -n istio-system -o jsonpath='{.items[0].status.hostIP}')
检查 Istio Ingress Gateway 的服务类型
[root@k8s-master networking]# kubectl -n istio-system get service istio-ingressgateway
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
istio-ingressgateway LoadBalancer 10.96.2.197 <pending> 15021:30612/TCP,80:30004/TCP,443:31950/TCP,31400:30724/TCP,15443:32317/TCP 121m
应用默认目标规则
给各个服务创建“DestinationRule”
在使用istio控制bookinfo版本路由之前,需要在目标规则中定义好可用的版本,命名为subsets.
[root@k8s-master networking]# kubectl apply -f destination-rule-all.yaml
[root@k8s-master networking]# kubectl get destinationrules
NAME HOST AGE
details details 28s
productpage productpage 28s
ratings ratings 28s
reviews reviews 28s