K8S v1.22.5 安装 Istio-v1.14.1


1. 简介

  Istio 是一个 Service Mesh 形态的用于服务治理的开放平台。其中 “Service Mesh 形态" 可以理解为 Istio 实现了 Service Mesh,它是第二代 Service Mesh 的典型代表,从 2017 年 5 月发布第一个版本 0.1 开始就被广泛关注,直到现在成为被业界公认 Service Mesh 最成功的实现;"开放平台" 是指其本身是一个开源项目,最初是由 Google、IBM 和 Lyft 联合创建的;"服务" 可以简单的理解为微服务或者单个应用,是 Istio 治理的对象,而 "治理" 也正是 Istio 提供的功能,包括服务的流量管理、安全和可观测性。这里先对这几种治理做一个简单的阐释,在后面的文章中我们会做更详细的说明。

  • 流量管理:Istio 通过简单的规则配置和流量路由,可以控制服务之间的调用的流量和 API 调用。简化了熔断、超时和重试等配置,并且可以轻松设置 A/B 测试和金丝雀发布等任务。
  • 安全:Istio 管理服务间通信的认证机制、通道加密服务和访问授权,可以保障服务通信的安全性,并且所有的这些功能都不必更改应用程序。
  • 可观测性:Istio 具备强大的链路追踪、监控和日志记录能力,从而方便了解服务的运行状况,发现并解决问题。

Istio 服务网格从逻辑上分为数据平面控制平面

  数据平面由一组以 Sidecar 方式部署的智能代理(Envoy)组成,所有进入和流出服务的流量都会被 Envoy 拦截,并与控制面进行交互,根据配置执行相应的通信功能。Envoy 之所以称之为智能,是因为 Envoy 相对于其他代理来说有着更丰富的治理能力和灵活的配置方式,并且支持各种插件可用于扩展流量治理能力,并生成遥测数据。

  控制平面上,Istio 由三个组件( Pilot、Citadel、Galley )整合成了一个单进程、多模块的 istiod,极大的降低了部署的复杂度。其中 Pilot 组件负责提供服务发现、智能路由(如金丝雀发布)和弹性功能(如超时、重试);Citadel 负责安全,管理密钥和证书;Galley 负责对配置的验证和处理等功能。需要注意的是,整个运行流程需要这些组件协同工作。Istiod 作为一种全新的设计,构建了一套标准的控制面规范,主要提供服务发现、规则配置和证书管理等功能,并向数据平面传递这些信息。

Istio 介绍

从根本上讲,Istio 的工作原理是以 Sidcar 的形式将 Envoy 的扩展版本作为代理布署到每个微服务中。

2. 环境

  • k8s-v1.22.5 集群
主机 IP
master 192.168.10.100
node01 192.168.10.101
node02 192.168.10.102
  • istio-v1.14.1
  • ingress-nginx-v1.0.0
  • metallb

3. K8S 集群安装 istio

下载安装包,配置环境变量

[root@master ~]#wget http://49.232.8.65/istio/istio-1.14.1-linux-amd64.tar.gz
......
[root@master ~]#mkdir /application
[root@master ~]#tar zxvf istio-1.14.1-linux-amd64.tar.gz -C /application/
......
[root@master ~]#ll /application/istio-1.14.1/
总用量 28
drwxr-x---  2 root root    22 6月   8 10:10 bin
-rw-r--r--  1 root root 11348 6月   8 10:10 LICENSE
drwxr-xr-x  5 root root    52 6月   8 10:10 manifests
-rw-r-----  1 root root   796 6月   8 10:10 manifest.yaml
-rw-r--r--  1 root root  6016 6月   8 10:10 README.md
drwxr-xr-x 23 root root  4096 6月   8 10:10 samples
drwxr-xr-x  3 root root    57 6月   8 10:10 tools
[root@master ~]#ll /application/istio-1.14.1/bin/
总用量 83676
-rwxr-xr-x 1 root root 85684224 6月   8 10:10 istioctl
[root@master ~]#echo "export PATH=$PATH:/application/istio-1.14.1/bin" >> /etc/profile
[root@master ~]#tail -n 1 /etc/profile
export PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/root/bin:/application/istio-1.14.1/bin
[root@master ~]#source /etc/profile

安装 istio

docker pull docker.io/istio/pilot:1.14.1
docker pull docker.io/istio/proxyv2:1.14.1
# 使用 demo 配置文件安装,它具有一组良好的测试默认值,但还有其他配置文件用于生产或性能测试
# 集群内存要足够
[root@master ~]# istioctl install --set profile=demo -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.14.  Please take a few minutes to tell us about your install/upgrade experience!  https://forms.gle/yEtCbt45FZ3VoDT5A
[root@master ~]# kubectl get pods -n istio-system -o wide
NAME                                    READY   STATUS    RESTARTS   AGE     IP              NODE     NOMINATED NODE   READINESS GATES
istio-egressgateway-575d8bd99b-sqdm9    1/1     Running   0          9m22s   10.244.140.70   node02   <none>           <none>
istio-ingressgateway-6668f9548d-dh656   1/1     Running   0          9m22s   10.244.140.69   node02   <none>           <none>
istiod-8495d444bb-zxfls                 1/1     Running   0          10m     10.244.140.68   node02   <none>           <none>

# 添加名称空间的标签,当部署应用后,告诉 istio 去自动的注入 Envoy sidecar 代理,这里是 default
# istio-injection=disabled 的命名空间是不会流入 sidecar 的
[root@master ~]# kubectl get ns
NAME              STATUS   AGE
default           Active   159m
istio-system      Active   3m31s
kube-node-lease   Active   159m
kube-public       Active   159m
kube-system       Active   159m
[root@master ~]# kubectl label namespace default istio-injection=enabled
namespace/default labeled

# 如何取消注入
[root@master ~]# kubectl label namespaces default istio-injection-
namespace/default labeled
[root@master ~]# kubectl describe ns default
Name:         default
Labels:       istio-injection=enabled
              kubernetes.io/metadata.name=default
Annotations:  <none>
Status:       Active

No resource quota.

No LimitRange resource.

如果istio注入的ns中有容器启动失败,istio-init 容器报错

-A ISTIO_OUTPUT -o lo -m owner ! --gid-owner 1337 -j RETURN
-A ISTIO_OUTPUT -m owner --gid-owner 1337 -j RETURN
-A ISTIO_OUTPUT -d 127.0.0.1/32 -j RETURN
-A ISTIO_OUTPUT -j ISTIO_REDIRECT
COMMIT
2023-12-04T03:09:22.457420Z     info    Running command: iptables-restore --noflush /tmp/iptables-rules-1701659362457101497.txt4192592907
2023-12-04T03:09:22.460619Z     error   Command error output: xtables parameter problem: iptables-restore: unable to initialize table 'nat'

Error occurred at line: 1
Try `iptables-restore -h' or 'iptables-restore --help' for more information.
2023-12-04T03:09:22.460644Z     error   Failed to execute: iptables-restore --noflush /tmp/iptables-rules-1701659362457101497.txt4192592907, exit status 2

是因为 iptables模块未被加载,对应主机执行

modprobe ip_tables
modprobe iptable_filter

卸载 istio:

https://istio.io/latest/docs/setup/install/istioctl/#uninstall-istio

4. 部署示例应用程序

部署 Bookinfo 示例应用程序

[root@master /application/istio-1.14.1]# ls
bin  LICENSE  manifests  manifest.yaml  README.md  samples  tools

[root@master /application/istio-1.14.1]# kubectl apply -f samples/bookinfo/platform/kube/bookinfo.yaml 
service/details created
serviceaccount/bookinfo-details created
deployment.apps/details-v1 created
service/ratings created
serviceaccount/bookinfo-ratings created
deployment.apps/ratings-v1 created
service/reviews created
serviceaccount/bookinfo-reviews created
deployment.apps/reviews-v1 created
deployment.apps/reviews-v2 created
deployment.apps/reviews-v3 created
service/productpage created
serviceaccount/bookinfo-productpage created
deployment.apps/productpage-v1 created

查看

# 应用程序将启动。随着每个 pod 准备就绪,Istio sidecar 将随之部署
# 我的 pod 启动时间非常长,等到所有 pod 都报告 READY2/2 和 STATUSRunning 后再进行下一步,耐心等待
[root@master /application/istio-1.14.1]# kubectl get pods
NAME                              READY   STATUS    RESTARTS   AGE
details-v1-7d88846999-hrcgp       2/2     Running   0          16m
productpage-v1-7795568889-92mdm   2/2     Running   0          16m
ratings-v1-754f9c4975-ckf5z       2/2     Running   0          16m
reviews-v1-55b668fc65-lsfjs       2/2     Running   0          16m
reviews-v2-858f99c99-7nw82        2/2     Running   0          16m
reviews-v3-7886dd86b9-cnjdh       2/2     Running   0          16m
[root@master /application/istio-1.14.1]# kubectl get service
NAME          TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)    AGE
details       ClusterIP   10.100.172.185   <none>        9080/TCP   16m
kubernetes    ClusterIP   10.96.0.1        <none>        443/TCP    3h7m
productpage   ClusterIP   10.97.47.169     <none>        9080/TCP   16m
ratings       ClusterIP   10.102.140.67    <none>        9080/TCP   16m
reviews       ClusterIP   10.108.151.245   <none>        9080/TCP   16m

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

[root@master ~]# 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>

5. 向外部流量打开应用程序

Bookinfo 应用程序已部署,但无法从外部访问。为了使其可访问,您需要创建一个 Istio Ingress Gateway,它将路径映射到网格边缘的路由。

将此应用程序与 Istio 网关关联

[root@master ~]# kubectl apply -f /application/istio-1.14.1/samples/bookinfo/networking/bookinfo-gateway.yaml
gateway.networking.istio.io/bookinfo-gateway created
virtualservice.networking.istio.io/bookinfo created

确保配置没有问题

[root@master ~]# istioctl analyze

✔ No validation issues found when analyzing namespace: default.

5.1 确定入口 IP 和端口

设置访问网关的 INGRESS_HOSTINGRESS_PORT 变量

执行以下命令来确定您的 Kubernetes 集群是否在支持外部负载均衡器的环境中运行:

[root@master ~]# kubectl get svc istio-ingressgateway -n istio-system
NAME                   TYPE           CLUSTER-IP      EXTERNAL-IP   PORT(S)                                                                      AGE
istio-ingressgateway   LoadBalancer   10.98.234.126   <pending>     15021:30921/TCP,80:32314/TCP,443:31968/TCP,31400:32530/TCP,15443:31268/TCP   3h6m

如果 EXTERNAL-IP 设置了 IP,则您的环境具有可用于入口网关的外部负载均衡器。如果 EXTERNAL-IP 值为 <none>(或永久 <pending>),则您的环境不为入口网关提供外部负载均衡器。在这种情况下,您可以使用服务的节点端口 访问网关。

没有 EIP 解决链接

1. 安装 metallb
2. 安装 ingress-controller
3. 再次查看 istio-ingressgateway
# 已经获取 EIP
[root@master ~]# kubectl get svc istio-ingressgateway -n istio-system
NAME                   TYPE           CLUSTER-IP      EXTERNAL-IP      PORT(S)                                                                      AGE
istio-ingressgateway   LoadBalancer   10.98.234.126   192.168.10.170   15021:30921/TCP,80:32314/TCP,443:31968/TCP,31400:32530/TCP,15443:31268/TCP   3h19m

如果您确定您的环境具有外部负载平衡器,进行下面的操作。

设置入口 IP 和端口:

# 可将环境变量写进 /etc/profile 中
[root@master ~]# export INGRESS_HOST=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.status.loadBalancer.ingress[0].ip}')
[root@master ~]# export INGRESS_PORT=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.spec.ports[?(@.name=="http2")].port}')
[root@master ~]# export SECURE_INGRESS_PORT=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.spec.ports[?(@.name=="https")].port}')

在某些环境中,负载均衡器可能会使用主机名而不是 IP 地址。在这种情况下,入口网关的 EXTERNAL-IP 值将不是 IP 地址,而是主机名,上述命令将无法设置 INGRESS_HOST 环境变量。使用以下命令更正该 INGRESS_HOST 值:

export INGRESS_HOST=$(kubectl -n istio-system get service istio-ingressgateway -o jsonpath='{.status.loadBalancer.ingress[0].hostname}')

确保 IP 地址和端口已成功分配给每个环境变量

[root@master ~]# echo "$INGRESS_HOST"
192.168.10.170
[root@master ~]# echo "$INGRESS_PORT"
80
[root@master ~]# echo "$SECURE_INGRESS_PORT"
443

设置 GATEWAY_URL

# 可将环境变量写进 /etc/profile 中
[root@master ~]# export GATEWAY_URL=$INGRESS_HOST:$INGRESS_PORT
[root@master ~]# echo "$GATEWAY_URL"
192.168.10.170:80

5.2 验证外部访问

通过使用浏览器查看 Bookinfo 产品页面,确认可以从外部访问 Bookinfo 应用程序。

运行以下命令以检索 Bookinfo 应用程序的外部地址

[root@master ~]# echo "http://$GATEWAY_URL/productpage"
http://192.168.10.170:80/productpage

将上一个命令的输出粘贴到您的 Web 浏览器中,并确认显示 Bookinfo 产品页面。

6. 安装仪表盘

Istio 集成了几个不同的监控应用程序。这些可以帮助您了解服务网格的结构、显示网格的拓扑并分析网格的健康状况。

使用以下说明部署 Kiali 仪表板以及 PrometheusGrafanaJaeger

安装 kali 和其他插件

[root@master ~]# kubectl apply -f /application/istio-1.14.1/samples/addons
serviceaccount/grafana created
configmap/grafana created
service/grafana created
deployment.apps/grafana created
configmap/istio-grafana-dashboards created
configmap/istio-services-grafana-dashboards created
deployment.apps/jaeger created
service/tracing created
service/zipkin created
service/jaeger-collector created
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
serviceaccount/prometheus created
configmap/prometheus created
clusterrole.rbac.authorization.k8s.io/prometheus created
clusterrolebinding.rbac.authorization.k8s.io/prometheus created
service/prometheus created
deployment.apps/prometheus created

# 下面命令失败重复运行
[root@master ~]# kubectl rollout status deployment/kiali -n istio-system
Waiting for deployment "kiali" rollout to finish: 0 of 1 updated replicas are available...
deployment "kiali" successfully rolled out

[root@master ~]# kubectl get pods,svc -n istio-system
NAME                                        READY   STATUS    RESTARTS   AGE
pod/grafana-6c5dc6df7c-zzb5q                1/1     Running   0          44s
pod/istio-egressgateway-575d8bd99b-sqdm9    1/1     Running   0          8h
pod/istio-ingressgateway-6668f9548d-dh656   1/1     Running   0          8h
pod/istiod-8495d444bb-zxfls                 1/1     Running   0          8h
pod/jaeger-9dd685668-mwmqm                  1/1     Running   0          44s
pod/kiali-5db6985fb5-chctb                  1/1     Running   0          43s
pod/prometheus-699b7cc575-4lxbs             2/2     Running   0          43s

NAME                           TYPE           CLUSTER-IP       EXTERNAL-IP      PORT(S)                                                                      AGE
service/grafana                ClusterIP      10.101.225.230   <none>           3000/TCP                                                                     44s
service/istio-egressgateway    ClusterIP      10.107.140.240   <none>           80/TCP,443/TCP                                                               8h
service/istio-ingressgateway   LoadBalancer   10.98.234.126    192.168.10.170   15021:30921/TCP,80:32314/TCP,443:31968/TCP,31400:32530/TCP,15443:31268/TCP   8h
service/istiod                 ClusterIP      10.97.201.157    <none>           15010/TCP,15012/TCP,443/TCP,15014/TCP                                        8h
service/jaeger-collector       ClusterIP      10.101.114.182   <none>           14268/TCP,14250/TCP,9411/TCP                                                 44s
service/kiali                  ClusterIP      10.107.178.217   <none>           20001/TCP,9090/TCP                                                           43s
service/prometheus             ClusterIP      10.105.102.86    <none>           9090/TCP                                                                     43s
service/tracing                ClusterIP      10.98.109.173    <none>           80/TCP,16685/TCP                                                             44s
service/zipkin                 ClusterIP      10.111.133.26    <none>           9411/TCP                                                                     44s

修改 kiali 的服务,将类型改为 LoadBalancer

[root@master ~]# kubectl edit svc kiali -n istio-system
......
     46   type: ClusterIP
......
# 修改此处为 type: LoadBalancer
# 在没有安装 metallb 产品的情况下,可以将该服务类型改为 NodePort
[root@master ~]# kubectl edit svc kiali -n istio-system
service/kiali edited

访问 Kiali 仪表板

配置 Service 为 LoadBalancer 类型

检查一下 kiali service 的类型是不是 LoadBalancer 类型,有没有获取 EIP

[root@master ~]# istioctl dashboard kiali
http://localhost:20001/kiali
[root@master ~]# kubectl get pods,svc -n istio-system
NAME                                        READY   STATUS    RESTARTS   AGE
pod/grafana-6c5dc6df7c-wt9wq                1/1     Running   0          4m7s
pod/istio-egressgateway-575d8bd99b-wq5fv    1/1     Running   0          20m
pod/istio-ingressgateway-6668f9548d-2nt77   1/1     Running   0          20m
pod/istiod-8495d444bb-xm6lw                 1/1     Running   0          21m
pod/jaeger-9dd685668-9hp2t                  1/1     Running   0          4m7s
pod/kiali-5db6985fb5-pnkvw                  1/1     Running   0          4m7s
pod/prometheus-699b7cc575-nc86z             2/2     Running   0          4m7s

NAME                           TYPE           CLUSTER-IP       EXTERNAL-IP      PORT(S)                                                                      AGE
service/grafana                ClusterIP      10.99.147.179    <none>           3000/TCP                                                                     4m7s
service/istio-egressgateway    ClusterIP      10.101.226.2     <none>           80/TCP,443/TCP                                                               20m
service/istio-ingressgateway   LoadBalancer   10.106.154.219   192.168.10.170   15021:30361/TCP,80:30766/TCP,443:32089/TCP,31400:32656/TCP,15443:31882/TCP   20m
service/istiod                 ClusterIP      10.108.100.170   <none>           15010/TCP,15012/TCP,443/TCP,15014/TCP                                        21m
service/jaeger-collector       ClusterIP      10.100.230.173   <none>           14268/TCP,14250/TCP,9411/TCP                                                 4m7s
service/kiali                  LoadBalancer   10.99.87.90      192.168.10.171   20001:31148/TCP,9090:32497/TCP                                               4m7s
service/prometheus             ClusterIP      10.106.49.15     <none>           9090/TCP                                                                     4m7s
service/tracing                ClusterIP      10.101.14.242    <none>           80/TCP,16685/TCP                                                             4m7s
service/zipkin                 ClusterIP      10.108.155.153   <none>           9411/TCP                                                                     4m7s

访问:http://192.168.10.171:20001/kiali

初始用户密码admin/admin


官方文档

官方入门安装文档

istio 简介和基础组件原理(服务网格 Service Mesh)

Istio 入门:架构原理及在 k8s 部署

istio 在 k8s 中的部署、移除、部署应用案例

istio-sidecar 自动注入

istio 在 k8s 中的部署、移除、部署应用案例

ISTIO 学习笔记:ISTIO 及 KIALI 的安装与配置

自从用了 Kiali 以后才知道,配置 Istio 的 流量管理 是如此容易

马哥亲讲 istio v1.4.0


posted @ 2022-07-10 23:31  公博义  阅读(846)  评论(0编辑  收藏  举报