kubernetes 使用Kustomize替换将一个库中的值替换为另一个库中的值?

3vpjnl9f  于 2023-08-03  发布在  Kubernetes
关注(0)|答案(1)|浏览(170)

我正在更新我的一些Kubernetes配置,以在kustomize中使用'replacements''resources',因为'vars''bases'已经被弃用。
之前,我在base(/base/secrets/)中使用了'vars',如下所示:

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization

secretGenerator:
- name: test_secret
  env: secret.env

vars:
- name : SECRET_VALUE
  objref:
    kind: Secret
    name: test_secret
    apiVersion: v1
  fieldref:
    fieldpath: metadata.name

字符串
此基础用于不同服务的各种覆盖:

namespace: test-overlay

bases:
- ../../base/secrets/
- ../../base/service/


现在,对于'resources''replacements',我的理解是不可能像以前那样从/base/secrets/替换/base/service/中的值。我可以将'replacement'应用到覆盖层本身中,并将目标定位到我想要修改的基础上,但为了重用和易用性,我更愿意从基础上执行操作。
我想这么做

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization

secretGenerator:
- name: test_secret
  env: secret.env

replacements:
- source:
    name: test_secret
    kind: Secret
  targets:
  - select:
      kind: Deployment
      name: service
    fieldPaths:
    - spec.template.spec.<field>


'replacements'指令中,spec.template.spec.<field>是我试图替换的Deployment资源中的字段。
我正在使用kustomize版本v5.1.0
如何让'replacements'瞄准其他基地,以便它们可以从任何覆盖层使用?这种情况下的最佳做法是什么?
我尝试在覆盖本身中应用'替换',并将目标定位到我想要修改的基础上,如下所示:

namespace: test-overlay

resources:
- ../../base/secrets/
- ../../base/service/

replacements:
- source:
    kind: Secret
    name: test_secret
  targets:
  - select:
      kind: Deployment
      name: service
    fieldPaths:
    - spec.template.spec.<field>


虽然这确实将替换应用到服务中,但对我来说这不是一个令人满意的解决方案,因为我有多个覆盖层,它们都需要在不同的部署中使用相同的替换。我更愿意在一个基底中定义一次替换,而不是必须在每个覆盖层中定义它。

编辑:更清晰的最小可再现示例

/base
  /secrets
    kustomization.yaml
  /service
    deployment.yaml
    kustomization.yaml
/overlays
  /test-overlay
    kustomization.yaml


/secrets/实现为:

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization

secretGenerator:
- name: test_secret
  env: secret.env

replacements:
- source:
    name: test_secret
    kind: Secret
  targets:
  - select:
      kind: Deployment
      name: service
    fieldPaths:
    - spec.template.spec.volumes.name


这就是/service/

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
    
resources:
- deployment.yaml

---

apiVersion: apps/v1
kind: Deployment
metadata:
  name: service
spec:
  template:
    spec:
      volumes:
      - name: placeholder_value
        emptyDir: {}


/test-overlay/

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization

namespace: test-overlay

resources:
- ../../base/secrets/
- ../../base/service/


我已经尝试在测试覆盖kustomization文件中包含'replacements',它确实可以工作,但不如让替换在base中定义好

vmjh9lq9

vmjh9lq91#

谢谢你用一个例子更新你的问题。
我在这里发布的答案仍然是在多个覆盖层之间共享替换配置的正确解决方案,但在replacement语法中存在一些错误:您不能以spec.template.spec.volumes.name为目标,因为volumes是一个列表,没有name属性。
您只能使用[name=value]样式选择器来定位列表元素,所以:

replacements:
  - source:
      name: test_secret
      kind: Secret
    targets:
      - select:
          kind: Deployment
          name: service
        fieldPaths:
          - spec.template.spec.volumes.[name=placeholder_value].name

字符串
kustomization.yaml只能对kustomization.yaml发出的资源应用转换(标签、补丁、替换等)--这意味着,如果你想让转换影响所有资源,就需要在“最外层”的kustomization中应用。
这意味着你不能在一个“基础”中放置一些会修改叠加中生成的资源的东西。
但是别担心,有一个解决办法!Components允许重用kustomization片段。如果我们将您的替换配置移动到组件中,我们可以获得您想要的行为。
例如,这里有一个具有基础和两个覆盖层的项目:

.
├── base
│   ├── deployment.yaml
│   └── kustomization.yaml
├── components
│   └── replace-username-password
│       └── kustomization.yaml
└── overlay
    ├── env1
    │   └── kustomization.yaml
    └── env2
        └── kustomization.yaml


base/deployment.yaml看起来像这样:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: example
spec:
  replicas: 2
  template:
    spec:
      containers:
        - name: example
          image: docker.io/alpine:latest
          command:
            - sleep
            - inf
          env:
            - name: USER_NAME
              value: update-via-replacement
            - name: USER_PASSWORD
              value: update-via-replacement


base/kustomization.yaml看起来像:

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
commonLabels:
  app: replacement-example

resources:
  - deployment.yaml

secretGenerator:
  - name: example
    literals:
      - password=secret

configMapGenerator:
  - name: example
    literals:
      - username=alice


因此base目录会生成Deployment、Secret和ConfigMap。有两个叠加,env1env2。在这两个覆盖层中,我想应用相同的替换配置,所以我把它放在components/replace-username-password/kustomization.yaml中:

apiVersion: kustomize.config.k8s.io/v1alpha1
kind: Component

replacements:
  - source:
      kind: ConfigMap
      name: example
      fieldPath: data.username
    targets:
      - select:
          kind: Deployment
          name: example
        fieldPaths:
          - spec.template.spec.containers.[name=example].env.[name=USER_NAME].value
  - source:
      kind: Secret
      name: example
      fieldPath: data.password
    targets:
      - select:
          kind: Deployment
          name: example
        fieldPaths:
          - spec.template.spec.containers.[name=example].env.[name=USER_PASSWORD].value


现在,在overlays/env1/kustomization.yaml中,我可以使用这个组件:

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
commonLabels:
  envName: env1

resources:
  - ../../base

components:
  - ../../components/replace-username-password


overlays/env2中也一样:

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
commonLabels:
  envName: env2

resources:
  - ../../base

components:
  - ../../components/replace-username-password

相关问题