K8s:渐进式入门服务网格 Istio (一)

对每个人而言,真正的职责只有一个:找到自我。然后在心中坚守其一生,全心全意,永不停息。所有其它的路都是不完整的,是人的逃避方式,是对大众理想的懦弱回归,是随波逐流,是对内心的恐惧 ——赫尔曼·黑塞《德米安》

写在前面


  • 分享一些 Istio 的学习笔记
  • 博文内容涉及:
    • istio 下载安装
    • 一个 Demo 运行
    • 什么是 istio,服务网格等概念介绍
    • istio 架构组成,应用场景等
  • 理解不足小伙伴帮忙指正

对每个人而言,真正的职责只有一个:找到自我。然后在心中坚守其一生,全心全意,永不停息。所有其它的路都是不完整的,是人的逃避方式,是对大众理想的懦弱回归,是随波逐流,是对内心的恐惧 ——赫尔曼·黑塞《德米安》


关于 服务网格是什么,istio 是什么,这里先不讲理论,安装下实体会下, istio 提供一些很不错的 Demo 给我们学习,个人感觉 istio 的部分功能是和 Spring Cloud Gateway 有重合的地方。只不过解决方式考虑的角度不通,Spring Cloud Gateway 是面向 Java 微服务治理的解决方案, istio 是非侵入式的,与语言无关,更多的是从部署角度考虑,属于基础设施的角度来解决微服务的服务治理问题。

整体上讲,这是一种发展趋势:服务治理业务逻辑,编写语言 逐步 解耦,服务治理能力下沉到 基础设施,把微服务中一些需要编程语言提供能力的功能抽象,建模出 服务网格 等以基础设施提供能力的方式,编程语言只用来提供业务能力,通过基础设施来提供无侵入的通信控制、安全、可观测性、灰度发布等治理能力。

下载安装

下载

https://istio.io/latest/docs/setup/getting-started/#download

这里如果需要加代理可以加一下代理(需要有科学上网之类的工具) -x 192.168.26.1:49757

1
2
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$curl -L https://istio.io/downloadIstio | sh -

或者其他机器下载上传下

1
2
3
4
PS W:\Downloads> scp .\istio-1.16.2-linux-amd64.tar.gz  root@192.168.26.100:~/ansible/istio/
root@192.168.26.100's password:
istio-1.16.2-linux-amd64.tar.gz 100% 24MB 109.2MB/s 00:00
PS W:\Downloads>

解压安装包

1
2
3
4
5
6
7
8
9
10
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$ls
istio-1.16.2-linux-amd64.tar.gz
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$tar -zxvf istio-1.16.2-linux-amd64.tar.gz
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio/istio-1.16.2]
└─$ls
bin LICENSE manifests manifest.yaml README.md samples tools
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio/istio-1.16.2]
└─$

安装中常用的目录有两个:

  • 示例应用程序 samples/
  • 客户端二进制 文件 bin/

配置 istioctl 为可执行文件,测试

1
2
3
4
5
6
7
8
9
10
11
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio/istio-1.16.2/bin]
└─$ls
istioctl
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio/istio-1.16.2/bin]
└─$cd ..
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio/istio-1.16.2]
└─$mv bin/istioctl /usr/local/bin/
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio/istio-1.16.2]
└─$istioctl version
no running Istio pods in "istio-system"
1.16.2

安装

使用 istioctl 工具安装 istio,可用通过 --help 查看相关的参数

1
2
3
4
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$istioctl install --help
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$istioctl install --set profile=demo --skip-confirmation

在安装的时候我们可以选择安装配置文件,profile=demo这里我们选择 Demo

1
2
3
4
5
6
7
8
9
10
11
12
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$istioctl install --set profile=demo --skip-confirmation
✔ 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.16. Please take a few minutes to tell us about your install/upgrade experience! https://forms.gle/99uiMML96AmsXY5d6
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$

使用 Demo 配置文件安装 Istio,它为我们提供了大多数用于评估和培训的功能,其他配置文件

  • Default : 建议用于生产部署并配置 IstioOperatorAPI 的默认设置。默认情况下执行大多数规则,您可以根据您的要求自定义配置。
  • Demo — 您可以使用它来尝试 Istio 和学习,尤其是当您使用 Minikube 或资源有限的设置时。对于运行示例应用程序,这是最合适的配置文件,我们将在演示中使用它。
  • Minimal —它包含最少量的功能,仅用于支持流量管理。
  • Remote — 如果你正在运行多个 Kubernetes 集群并且想使用 Istio 来管理多集群环境,那么这是最合适的配置文件。它为您提供了一个共享的控制平面,可以从一个地方管理您的所有集群
  • Empty — 这个配置文件没有部署任何东西,如果你想自定义 Istio 并从一个基本配置文件开始,你可以使用它
  • Separate — 这已被弃用且不推荐,它仅用于支持遗留功能。

添加命名空间标签,指示 Istio 自动注入 Envoy。

1
2
3
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl label namespace default istio-injection=enabled
namespace/default labeled

简单理解,就是在指定的命名空间为每个创建的 Pod 自动注入一个代理容器。

测试配置

现在已经安装了 Istio 并将其配置为自动将 sidecar 容器(或者说 proxy 容器)注入到您的默认命名空间,安装示例 Book Info 应用程序并查看 Istio 是否正常工作

有四个微服务:details、ratings、reviewsproductpage。 reviews 微服务包含三个版本的 pod,每个版本都标记为 v1、v2 和 v3。其余微服务只有一个版本 (v1)

查看 YAML 文件信息,这里为了方便我们找了一个之前的插件来看下

1
2
3
4
5
6
7
8
9
10
11
12
13
14
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl-score istio-1.16.2/samples/bookinfo/platform/kube/bookinfo.yaml | grep v1
apps/v1/Deployment details-v1 💥
apps/v1/Deployment productpage-v1 💥
apps/v1/Deployment ratings-v1 💥
apps/v1/Deployment reviews-v1 💥
apps/v1/Deployment reviews-v2 💥
apps/v1/Deployment reviews-v3 💥
v1/Service details ✅
v1/Service productpage ✅
v1/Service ratings ✅
v1/Service reviews ✅
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$

应用 YAML 文件

1
2
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl apply -f istio-1.16.2/samples/bookinfo/platform/kube/bookinfo.yaml

查看配置的 服务信息

1
2
3
4
5
6
7
8
9
10
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
details ClusterIP 10.104.106.169 <none> 9080/TCP 70s
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 15d
productpage ClusterIP 10.107.234.149 <none> 9080/TCP 69s
ratings ClusterIP 10.100.251.135 <none> 9080/TCP 69s
reviews ClusterIP 10.105.63.97 <none> 9080/TCP 69s
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$

查看配置的 POD 信息。可以看到,每个 pod 中有两个就绪的容器,一个是 应用容器,一个是 作为 init 容器的 代理容器。

1
2
3
4
5
6
7
8
9
10
11
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl get pod
NAME READY STATUS RESTARTS AGE
details-v1-5ffd6b64f7-wfbl2 2/2 Running 0 57m
productpage-v1-979d4d9fc-hvh6j 2/2 Running 0 57m
ratings-v1-5f9699cfdf-6gnwh 2/2 Running 0 57m
reviews-v1-569db879f5-mp4ql 2/2 Running 0 57m
reviews-v2-65c4dc6fdc-sjbtl 2/2 Running 0 57m
reviews-v3-c9c4fb987-gbvgh 2/2 Running 0 57m
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$

应用程序将启动。当每个 pod 准备就绪时,Istio sidecar ,或者说代理将与其一起部署。Istio 正在 pod 中启动 Envoy sidecar 容器。这表明 Istio 正在自动注入 sidecars 边车 。

验证到目前为止一切正常。运行此命令以查看应用程序是否在集群内运行并通过检查响应中的页面标题来提供 HTML 页面:

1
2
3
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl exec "$(kubectl get pod -l app=ratings -o jsonpath='{.items[0].metadata.name}')" -c ratings -- curl -sS productpage:9080/productpage | grep -o "<title>.*</title>"
<title>Simple Bookstore App</title>

查看 Istio 入口网关 SVC 是否正常。这将提供一个外部 负载均衡器,用于访问网格内的服务,如果你的实验环境没有 LB,可以尝试 软 LB 或者使用 NodePort 的方式

1
2
3
4
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl -n istio-system get service istio-ingressgateway
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
istio-ingressgateway LoadBalancer 10.102.37.99 192.168.26.220 15021:31664/TCP,80:32106/TCP,443:30607/TCP,31400:31336/TCP,15443:30740/TCP 24m

Istio 在负载均衡器上公开了多个端口。在此示例中,我们需要在端口 80 上运行我们的应用程序,通过 192.168.26.220:80 访问

向外部流量开放应用程序

Bookinfo 应用程序已部署,但无法从外部访问。为了使其可访问,需要创建一个 Istio Ingress Gateway,它将路径映射到网格边缘的路由。上面的 LB 是 服务网格的总入口控制。现在需要一个应用的入口控制,所以需要创建 bookinfo-gateway 。

1
2
3
4
5
6
7
8
9
10
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl apply -f istio-1.16.2/samples/bookinfo/networking/bookinfo-gateway.yaml
gateway.networking.istio.io/bookinfo-gateway created
virtualservice.networking.istio.io/bookinfo created
┌──[root@vms100.liruilongs.github.io]-[~/ansible/helm]
└─$istioctl analyze

✔ No validation issues found when analyzing namespace: default.
┌──[root@vms100.liruilongs.github.io]-[~/ansible/helm]
└─$

在上面的命令中,创建 bookinfo-gateway 的同时,创建了一个 virtualservice ,这是一个 虚拟服务,在 istio 中,用于描述 流量路由的配置。即路由规则和服务提供能力的映射。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
spec:
hosts:
- '*'
gateways:
- bookinfo-gateway
http:
- match:
- uri:
exact: /productpage
- uri:
prefix: /static
- uri:
exact: /login
- uri:
exact: /logout
- uri:
prefix: /api/v1/products
route:
- destination:
host: productpage
port:
number: 9080
status: {}

这是一些测试动作,希望通过下面的命令来拼接出访问地址,非必须操作。

1
2
3
export INGRESS_HOST=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.status.loadBalancer.ingress[0].ip}')
export INGRESS_PORT=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.spec.ports[?(@.name=="http2")].port}')
export SECURE_INGRESS_PORT=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.spec.ports[?(@.name=="https")].port}')
1
2
3
4
5
6
7
8
┌──[root@vms100.liruilongs.github.io]-[~/ansible/helm]
└─$export GATEWAY_URL=$INGRESS_HOST:$INGRESS_PORT
┌──[root@vms100.liruilongs.github.io]-[~/ansible/helm]
└─$ echo "$GATEWAY_URL"
192.168.26.220:80
┌──[root@vms100.liruilongs.github.io]-[~/ansible/helm]
└─$echo "http://$GATEWAY_URL/productpage"
http://192.168.26.220:80/productpage

验证外部访问

尝试在浏览器上使用 Load Balancer IP 访问应用程序:

在这里插入图片描述

刷新它,会看到一个不同的页面出现:

在这里插入图片描述

再次刷新,你会看到另一个页面出现:

在这里插入图片描述

当我们部署应用程序时,我们实现了 ratings 微服务的三个版本,它以循环方式显示。这是 Istio 的默认路由策略,这表明 Istio 已安装并正常工作。那么这个路由规则是在哪里配置的

有时书评输出包含星级评分,有时则不包含。这是因为没有明确的默认服务版本可以路由到那个版本,Istio 以循环方式将请求路由到所有可用版本。

在这里插入图片描述

为了在网格中导流,Istio 需要知道所有的 endpoint 在哪和属于哪个服务。为了定位到 service registry(服务注册中心),Istio 会连接到一个服务发现系统。例如,如果您在 Kubernetes 集群上安装了 Istio,那么它将自动检测该集群中的服务和 endpoint。

默认情况下,Envoy 代理基于轮询调度模型在服务的负载均衡池内分发流量,按顺序将请求发送给池中每个成员,一旦所有服务实例均接收过一次请求后,重新回到第一个池成员。

和其他 Istio 配置一样,这些 API 也使用 Kubernetes 的自定义资源定义(CRD)来声明,您可以像示例中看到的那样使用 YAML 进行配置。

完成了这个 Demo ,对 Istio 有了大概了解,看一些理论性的东西。

什么是服务网格?

现代应用程序通常构建为 分布式微服务 集合,每个微服务集合执行一些离散的业务功能。服务网格是一个专用的基础设施层,您可以将其添加到您的应用程序中。它允许您透明地添加可观察性、流量管理和安全性等功能,而无需将它们添加到您自己的代码中。术语“服务网格”描述了用于实现此模式的软件类型,以及使用该软件时创建的安全域或网络域。

服务网络 是云原生技术中不可不谈的一部分,CNCF(Cloud Native Computing Foundation(云原生计算基金会))对云原生定义:云原生技术有利于各组织在公有云、私有云和混合云等新型动态环境中,构建和运行可弹性扩展的应用。云原生的代表技术包括容器、服务网格、微服务、不可变基础设施和声明式APl

随着分布式服务的部署(例如在基于 Kubernetes 的系统中)的规模和复杂性的增加,它会变得更难理解和管理。它的要求可以包括发现、负载平衡、故障恢复、指标和监控。服务网格通常还可以满足更复杂的操作需求,例如 A/B 测试、金丝雀部署、速率限制、访问控制、加密和端到端身份验证

服务到服务的通信使分布式应用程序成为可能。随着服务数量的增长,在应用程序集群内和跨应用程序集群路由此通信变得越来越复杂。Istio 有助于降低这种复杂性,同时减轻开发团队的压力

服务网格 是一种云原生的、应用层的网络技术

  • 云原生:面向弹性、(微)服务化、去中心化业务场景
  • 应用层:以应用为中心,关注应用的发布、监控、恢复等
  • 网络:关注应用组件之间的接口、流量、数据、访问安全等

什么是 Istio ?

Istio 是一个开源 服务网格,它透明地分层到现有的分布式应用程序上。Istio 的强大功能提供了一种统一且更有效的方式来 保护、连接和监控 服务。

IstioGoogle、IBM、RedHat 等开源巨头成熟的项目运作与社区治理机制下快速发展:

  • lstio 作为第二代 Service Mesh 技术,通过基于 K8s 标准扩展的控制面带来了前所未有的灵活性及扩展能力,影响力远超更早出现的 Linkerd
  • Istio 背负巨大的使命,Google 希望在继 Kubernetes 成为容器编排的事实标准之后,打造另一杀手铜级别的技术,成为服务网格的事实标准
  • Google 与 IBM 大厂的加持,在资源及影响力层面远非 Buoyant 可比拟的
  • 众多厂商参与 Istio 社区,共同推进繁荣
  • 从企业级可用的 1.1 版本之后,社区每隔 3 个月发布一个大版本
  • 成立 Steering Committee,社区的运作、治理更加透明

Istio 专为可扩展性而设计,可以处理各种部署需求。Istio 的控制平面在 Kubernetes 上运行,您可以将部署在该集群中的应用程序添加到您的网格中,将网格扩展到其他集群,甚至连接 VM 或在 Kubernetes 外部运行的其他端点。

在这里插入图片描述

对于云原生应用,采用 Kubernetes 构建微服务部署和集群管理能力,采用 Istio 构建服务治理能力,将逐渐成为应用微服务转型的标准配置。

怎么运行的

Istio 有两个组件:数据平面控制平面

在这里插入图片描述

数据平面

数据平面是服务之间的通信。如果没有服务网格,网络就无法理解正在发送的流量,也无法根据流量的类型、来源或目的地做出任何决定。

服务网格使用代理来拦截您的所有网络流量,从而根据您设置的配置提供广泛的应用程序感知功能。

数据平面由一组Envoy 代理组成,与您在集群中启动的每个服务一起部署,或者与在 VM 上运行的服务一起运行。

控制平面

控制平面采用您所需的配置及其服务视图,并对代理服务器进行动态编程,随着规则或环境的变化更新它们。简单来讲,管理并配置代理来进行流量路由。

Istio 控制平面核心组件:

  • Pilot:为 Envoy sidecar 提供服务发现、用于智能路由的流量管理功能(例如,A/B 测试、金丝雀发布等)以及弹性功能(超时、重试、熔断器等)。
  • Citadel:通过内置的身份和证书管理,可以支持强大的服务到服务以及最终用户的身份验证。
  • Galley:Istio 的配置验证、提取、处理和分发组件。

功能特性

Istio 是实现负载均衡、服务到服务身份验证和监控的途径,几乎不需要更改服务代码。其强大的控制平面带来了重要的功能,包括:

  • 使用 TLS 加密、基于身份的强大身份验证和授权在集群中保护服务到服务的通信
  • HTTP、gRPC、WebSocket 和 TCP 流量的自动负载平衡
  • 通过丰富的路由规则、重试、故障转移和故障注入对流量行为进行细粒度控制
  • 支持访问控制、速率限制和配额的可插入策略层和配置 API
  • 集群内所有流量的自动指标、日志和跟踪,包括集群入口和出口

在这里插入图片描述

核心理念:

  1. 非侵入式 Sidecar 注入技术,将数据面组件注入到应用所在的容器,通过劫持应用流量来进行功能实现,应用无感知。
  2. 北向 API 基于 K8sCRD 实现,完全声明式,标准化。
  3. 数据面与控制面通过 xDS gRPC 标准化协议通信,支持订阅模式。

核心特性:

  1. 服务&流量治理:熔断,故障注入,丰富的负载均衡算法,限流,健康检查,灰度发布,蓝绿部署等
  2. 流量与访问可视化:提供应用级别的监控,分布式调用链,访问日志等
  3. 安全连接:通过 mTLS、认证、鉴权等安全措施帮助企业在零信任的网络中运行应用

应用场景

  • 灰度发布:版本升级平滑过渡的一种方式,金丝雀发布、蓝绿发布等;
  • 流重管理:负载均衡、连接池管理、熔断、故障注入等;
  • 访问可视化:监控数据采集、运行指标分析、应用拓扑和调用链展示等;
  • 应用场景:电商应用、政企业务、视频业务等。

访问仪表板

Istio 提供了许多可选的仪表板,您可以使用它们来挂钩您的网格。演示安装附带 Kiali 仪表板,它为您提供网格的拓扑结构以及流量如何流经它。 YAML 文件在下载的安装包里面

https://istio.io/latest/docs/ops/integrations/kiali/

1
2
3
4
5
6
7
8
9
10
11
12
13
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl apply -f istio-1.16.2/samples/addons/kiali.yaml
serviceaccount/kiali created
configmap/kiali created
clusterrole.rbac.authorization.k8s.io/kiali-viewer created
clusterrole.rbac.authorization.k8s.io/kiali created
clusterrolebinding.rbac.authorization.k8s.io/kiali created
role.rbac.authorization.k8s.io/kiali-controlplane created
rolebinding.rbac.authorization.k8s.io/kiali-controlplane created
service/kiali created
deployment.apps/kiali created
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$

修改一下,外部可以方式。

1
2
3
4
5
6
7
8
9
10
11
12
13
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl get svc -n istio-system kiali
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kiali ClusterIP 10.111.1.255 <none> 20001/TCP,9090/TCP 6m10s
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl patch svc -n istio-system kiali -p '{"spec":{"type": "LoadBalancer"}}'
service/kiali patched
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$kubectl get svc -n istio-system kiali
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kiali LoadBalancer 10.111.1.255 192.168.26.222 20001:31385/TCP,9090:30521/TCP 9m33s
┌──[root@vms100.liruilongs.github.io]-[~/ansible/istio]
└─$

在这里插入图片描述

查看 istio 相关的 CRD 对应的资源对象

在这里插入图片描述

这里 默认情况下 Graph 是无法使用的, 需要先部署 prometheus 相关,如果已经部署,需要修改 kiali 的 cm 配置文件,

1
2
3
4
5
6
7
8
9
external_services:
custom_dashboards:
enabled: true
istio:
root_namespace: istio-system
grafana:
url: "http://10.96.85.130:80"
prometheus:
url: http://release-name-kube-promethe-prometheus.default.svc.cluster.local:9090/

prometheus 的访问地址要写实际的,SVC DNS 域名地址

1
2
3
4
5
6
┌──[root@vms100.liruilongs.github.io]-[~]
└─$kubectl get svc -n default release-name-kube-promethe-prometheus
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
release-name-kube-promethe-prometheus ClusterIP 10.109.35.14 <none> 9090/TCP 13d
┌──[root@vms100.liruilongs.github.io]-[~]
└─$

在这里插入图片描述

这里的 grafana 可能有点问题,所以 无法看到流量视图,时间关系,没有深入研究,感兴趣的小伙伴可以看看。

博文部分内容参考

© 文中涉及参考链接内容版权归原作者所有,如有侵权请告知


https://istio.io/latest/zh/docs/concepts/traffic-management/

https://kiali.io/docs/installation/quick-start/

https://istio.io/latest/about/service-mesh/

https://betterprogramming.pub/getting-started-with-istio-on-kubernetes-e582800121ea

《华为云云原生黄金课程 09:Istio 服务网格快速入门》


© 2018-2023 liruilonger@gmail.com, All rights reserved. 保持署名-非商用-相同方式共享(CC BY-NC-SA 4.0)

发布于

2023-02-25

更新于

2024-03-26

许可协议

评论
Your browser is out-of-date!

Update your browser to view this website correctly.&npsb;Update my browser now

×