Kubernetes环境Dapr部署与应用

发布于2021-11-03,最后编辑于2024-10-25,全文约1755字,阅读时间约4分钟。

Kubernetes Helm Sidecar Dapr

Dapr Dashboard
Dapr Dashboard
更新记录
  • 2021-11-20

    • Dapr Runtime版本由v1.4.3更新至v1.5.0
  • 2022-04-30

    • Dapr Runtime版本由v1.5.0更新至v1.7.2
    • Redis版本由v6.2.6更新至v7.0.0
  • 2022-05-20

    • Dapr Runtime版本由v1.7.2更新至v1.7.3
  • 2022-06-23

    • Dapr Runtime版本由v1.7.3更新至v1.7.4
    • Redis版本由v7.0.0更新至v7.0.2
  • 2022-07-09

    • Dapr Runtime版本由v1.7.4更新至v1.8.0
  • 2022-07-24

    • Dapr Runtime版本由v1.8.0更新至v1.8.2
  • 2022-08-14

    • Dapr Runtime版本由v1.8.2更新至v1.8.4
    • Redis版本由v7.0.2更新至v7.0.4
  • 2022-10-16

    • Dapr Runtime版本由v1.8.4更新至v1.9.0
    • 新增Dapr CLI部署Dapr Runtime说明;
    • Redis版本由v7.0.4更新至v7.0.5
  • 2022-11-12

    • Dapr Runtime版本由v1.9.0更新至v1.9.3
  • 2022-12-08

    • Dapr Runtime版本由v1.9.3更新至v1.9.5
  • 2023-02-09

    • Dapr Runtime版本由v1.9.5更新至v1.9.6
  • 2023-02-18

    • Dapr CLI版本由v1.9.1更新至v1.10.0
    • Dapr Runtime版本由v1.9.6更新至v1.10.0
    • Redis版本由v7.0.5更新至v7.0.8
  • 2023-03-03

    • Dapr Runtime版本由v1.10.0更新至v1.10.2
  • 2023-03-22

    • Dapr Runtime版本由v1.10.2更新至v1.10.4
  • 2023-04-14

    • Dapr Runtime版本由v1.10.4更新至v1.10.5
    • Redis版本由v7.0.8更新至v7.0.10
  • 2023-06-02

    • Dapr Runtime版本由v1.10.5更新至v1.10.7
    • Redis版本由v7.0.10更新至v7.0.11
  • 2023-06-24

    • Dapr CLI版本由v1.10.0更新至v1.11.0
    • Dapr Runtime版本由v1.10.7更新至v1.11.1
  • 2023-07-24

    • Dapr Runtime版本由v1.11.1更新至v1.11.2
    • Redis版本由v7.0.11更新至v7.0.12
  • 2023-09-01

    • Dapr Runtime版本由v1.11.2更新至v1.11.3
  • 2024-01-01

    • Dapr CLI版本由v1.11.0更新至v1.12.0
    • Dapr Runtime版本由v1.11.3更新至v1.12.2
    • Redis版本由v7.0.12更新至v7.2.3
  • 2024-03-31

    • Dapr CLI版本由v1.12.0更新至v1.13.0
    • Dapr Runtime版本由v1.12.2更新至v1.13.1

概述

本文用于整理基于Kubernetes环境的Dapr部署与应用,并基于Redis部署状态管理发布/订阅组件。

随着各相关组件版本的更新,笔者将在验证通过后对本文进行补充和更新,请参考更新记录

本次演练环境为Kubernetes集群环境,环境配置可参考笔者另一篇笔记《Kubernetes集群部署笔记》。

本次演练使用Traefik作为Ingress Controller实现,环境配置可参考笔者另一篇笔记《Kubernetes环境Traefik部署与应用》。

组件版本

配置过程

部署Dapr运行时

本次演练中将Dapr Runtime部署至dapr-system命名空间,可根据需要替换。

根据需要选择使用Dapr CLI或Helm部署运行时组件。

  • 使用Dapr CLI部署

    安装Dapr CLI

    1curl -sL https://github.com/dapr/cli/releases/download/v1.13.0/dapr_linux_amd64.tar.gz | tar xzf - dapr
    2sudo mv ./dapr /usr/local/bin/dapr
    3sudo chown root:root /usr/local/bin/dapr
    4sudo chmod 755 /usr/local/bin/dapr
    

    安装运行时组件。

    1# --kubernetes              部署至Kubernetes集群
    2# --namespace dapr-system   指定命名空间
    3# --enable-ha               启用高可用模式
    4# --runtime-version 1.13.1  指定Dapr Runtime版本
    5dapr init --kubernetes --namespace dapr-system --enable-ha --runtime-version 1.13.1
    

    查看Dapr Runtime部署状态。

    1dapr status --kubernetes
    
  • 使用Helm部署(高级)

    添加Helm仓库。

    1helm repo add dapr https://dapr.github.io/helm-charts
    2helm repo update dapr
    

    安装运行时组件。

    1# --namespace dapr-system   指定命名空间
    2# global.ha.enabled=true    启用高可用模式
    3# global.ha.replicaCount=3  设置高可用模式下运行时组件的副本数
    4helm upgrade --install --namespace dapr-system --create-namespace \
    5  --set global.ha.enabled=true \
    6  --set global.ha.replicaCount=3 \
    7  dapr dapr/dapr
    

    安装Dapr Dashboard(可选)。

    1# --namespace dapr-system   指定命名空间
    2helm upgrade --install --namespace dapr-system \
    3  dapr-dashboard dapr/dapr-dashboard
    

配置Dapr Dashboard(可选)

  • 创建TLS证书Secret

    从已准备好的证书key文件和crt文件创建Secret

    1kubectl create secret tls local-choral-io-tls -n dapr-system --key=local.choral.io.key --cert=local.choral.io.crt
    
  • 配置BasicAuth认证

    首先,创建一个用于保存用户名和密码的Secret,其中的users字段内容可使用htpassword工具生成。本次演练中,认证usernamepassword都是admin

     1cat <<EOF | kubectl apply -f - > /dev/null
     2apiVersion: v1
     3kind: Secret
     4metadata:
     5  name: dapr-basicauth-secret
     6  namespace: dapr-system
     7data:
     8  users: |2 # htpasswd -nb admin admin | openssl base64
     9    YWRtaW46e1NIQX0wRFBpS3VOSXJyVm1EOElVQ3V3MWhReE5xWmM9Cg==
    10EOF
    

    创建一个Traefik中间件,用于对请求启用BasicAuth认证。

     1cat <<EOF | kubectl apply -f - > /dev/null
     2apiVersion: traefik.io/v1alpha1
     3kind: Middleware
     4metadata:
     5  name: dapr-basicauth
     6  namespace: dapr-system
     7spec:
     8  basicAuth:
     9    realm: traefik.local.choral.io
    10    secret: dapr-basicauth-secret
    11EOF
    
  • 配置dapr-dashboard服务的入口规则

    使用IngressRoute配置入口规则。

     1cat <<EOF | kubectl apply -f - > /dev/null
     2apiVersion: traefik.io/v1alpha1
     3kind: IngressRoute
     4metadata:
     5  name: dapr-dashboard
     6  namespace: dapr-system
     7spec:
     8  entryPoints:
     9    - websecure
    10  routes:
    11    - match: Host(\`dapr.local.choral.io\`)
    12      kind: Rule
    13      services:
    14        - name: dapr-dashboard
    15          kind: Service
    16          port: 8080
    17      middlewares:
    18        - name: dapr-basicauth
    19  tls:
    20    secretName: local-choral-io-tls
    21EOF
    

部署Redis实例

首先,部署一个用于演练的Redis实例。由于需要使用Redis Streams功能,要求Redis实例版本高于5.0.0

该实例仅用于演练环境,不可用于生产环境

  • 部署Redis实例(可选)

    本次演练中将Redis实例部署至data-redis命名空间,可根据需要替换。

     1cat <<EOF | kubectl apply -f - > /dev/null
     2apiVersion: v1
     3kind: Namespace
     4metadata:
     5  name: data-redis
     6---
     7apiVersion: v1
     8kind: PersistentVolumeClaim
     9metadata:
    10  name: redis-data
    11  namespace: data-redis
    12spec:
    13  storageClassName: local-path
    14  accessModes:
    15    - ReadWriteOnce
    16  resources:
    17    requests:
    18      storage: 2Gi
    19---
    20apiVersion: apps/v1
    21kind: Deployment
    22metadata:
    23  name: redis
    24  namespace: data-redis
    25spec:
    26  selector:
    27    matchLabels:
    28      app: redis
    29  strategy:
    30    type: Recreate
    31  template:
    32    metadata:
    33      labels:
    34        app: redis
    35    spec:
    36      containers:
    37        - image: redis:7.2.3-alpine
    38          name: redis
    39          ports:
    40            - containerPort: 6379
    41              name: redis
    42          volumeMounts:
    43            - name: redis-persistent-storage
    44              mountPath: /data
    45          resources:
    46            limits:
    47              memory: 128Mi
    48              cpu: 50m
    49      volumes:
    50        - name: redis-persistent-storage
    51          persistentVolumeClaim:
    52            claimName: redis-data
    53---
    54apiVersion: v1
    55kind: Service
    56metadata:
    57  name: redis-headless
    58  namespace: data-redis
    59spec:
    60  type: ClusterIP
    61  clusterIP: None
    62  selector:
    63    app: redis
    64  ports:
    65    - port: 6379
    66EOF
    

创建Dapr组件

  • 创建发布/订阅组件

     1cat <<EOF | kubectl apply -f - > /dev/null
     2apiVersion: dapr.io/v1alpha1
     3kind: Component
     4metadata:
     5  name: pubsub
     6  namespace: apps-choral
     7spec:
     8  type: pubsub.redis
     9  version: v1
    10  metadata:
    11  - name: redisHost
    12    value: redis-headless.data-redis:6379
    13  - name: redisPassword
    14    value: ""
    15  - name: redisDB
    16    value: 9
    17EOF
    
  • 创建状态管理组件

     1cat <<EOF | kubectl apply -f - > /dev/null
     2apiVersion: dapr.io/v1alpha1
     3kind: Component
     4metadata:
     5  name: statestore
     6  namespace: apps-choral
     7spec:
     8  type: state.redis
     9  version: v1
    10  metadata:
    11  - name: redisHost
    12    value: redis-headless.data-redis:6379
    13  - name: redisPassword
    14    value: ""
    15  - name: redisDB
    16    value: 9
    17EOF
    

验证组件状态

  • 创建示例应用

     1cat <<EOF | kubectl apply -f - > /dev/null
     2apiVersion: apps/v1
     3kind: Deployment
     4metadata:
     5  name: dapr-demo
     6  namespace: apps-choral
     7spec:
     8  selector:
     9    matchLabels:
    10      app: dapr-demo
    11  strategy:
    12    type: Recreate
    13  replicas: 1
    14  template:
    15    metadata:
    16      labels:
    17        app: dapr-demo
    18      annotations:
    19        dapr.io/enabled: "true"      # 启用Dapr集成
    20        dapr.io/app-id: "dapr-demo"  # Dapr应用标识
    21        dapr.io/app-port: "80"       # 应用访问端口
    22    spec:
    23      containers:
    24        - image: nginx:alpine
    25          imagePullPolicy: IfNotPresent
    26          name: dapr-demo
    27          ports:
    28            - containerPort: 80
    29          resources:
    30            limits:
    31              memory: 128Mi
    32              cpu: 200m
    33EOF
    

    打开示例应用Shell。本节中所有命令需要在示例应用的Shell中执行。

    1kubectl exec -it $(kubectl get pods -n apps-choral --selector=app=dapr-demo -o jsonpath="{.items[0].metadata.name}") -n apps-choral -- sh
    
  • 健康检查元数据

    1# 访问健康检查端点
    2curl http://localhost:3500/v1.0/healthz -w "%{http_code}\n"
    3# 204
    4
    5# 访问获取元数据端点
    6curl http://localhost:3500/v1.0/metadata -w "\n"
    7# {"id":"dapr-demo","actors":[],"extended":{"daprRuntimeVersion":"1.13.1"},"components":[{"name":"kubernetes","type":"secretstores.kubernetes","version":"v1","capabilities":[]},{"name":"statestore","type":"state.redis","version":"v1","capabilities":["ETAG","TRANSACTIONAL","ACTOR"]},{"name":"pubsub","type":"pubsub.redis","version":"v1","capabilities":[]}],"httpEndpoints":[],"subscriptions":[]}"subscriptions":[]}
    
  • 验证状态管理组件

     1# 保存一组状态
     2curl -X POST http://localhost:3500/v1.0/state/statestore -H "Content-Type: application/json" -d '[{ "key": "counter", "value": 1, "etag": "1" }]'
     3
     4# 读取某个状态
     5curl http://localhost:3500/v1.0/state/statestore/counter -H "Content-Type: application/json" -v -w "\n"
     6# < Etag: 1
     7# 1
     8
     9# 删除某个状态
    10curl -X DELETE -H "If-Match: 1" http://localhost:3500/v1.0/state/statestore/counter
    
  • 验证发布/订阅组件

    1curl -X POST http://localhost:3500/v1.0/publish/pubsub/orderStatus -H "Content-Type: application/json" -d '{"id": 1, "status": "completed"}' -w "%{http_code}\n"
    2# 204
    

参考资料