0

这个 Kubernetes Pod 对象有一个 Env,它的值是一个带单引号的字符串'"0.0.0.0/0"'

    clientSet, err := initClientSet()
    if err != nil {
        klog.ErrorS(err, "failed to init clientSet")
        return err
    }
    ctx := context.Background()

    job := &batchv1.Job{
        TypeMeta: metav1.TypeMeta{
            Kind:       "Job",
            APIVersion: "batch/v1",
        },
        ObjectMeta: metav1.ObjectMeta{
            Name: "tf-poc",
        },
        Spec: batchv1.JobSpec{
            Template: v1.PodTemplateSpec{
                Spec: v1.PodSpec{
                    Containers: []v1.Container{{
                        Name:            "tf-poc",
                        Image:           "nginx:1.9.4",
                        ImagePullPolicy: v1.PullIfNotPresent,
                        Env:             []v1.EnvVar{{Name: "TF_VAR_security_ips", Value: "'\"0.0.0.0/0\"'"}},
                    },
                    },
                    RestartPolicy: v1.RestartPolicyOnFailure,
                },
            },
        },
    }
    j, err := clientSet.BatchV1().Jobs("default").Create(ctx, job, metav1.CreateOptions{})

由 Kubernetes client-go(如上)或 Controller-runtime 创建后,一个单引号字符串变成了三个单引号。

spec:
  backoffLimit: 6
  completions: 1
  parallelism: 1
  selector:
    matchLabels:
      controller-uid: 53c93df0-b3b5-4dbc-b1d8-2a77316176a1
  template:
    metadata:
      creationTimestamp: null
      labels:
        controller-uid: 53c93df0-b3b5-4dbc-b1d8-2a77316176a1
        job-name: tf-poc
    spec:
      containers:
      - env:
        - name: TF_VAR_security_ips
          value: '''"0.0.0.0/0"'''

这是 Yaml 文件中的 Kubernetes 作业清单。

apiVersion: batch/v1
kind: Job
metadata:
  name: poc
spec:
  backoffLimit: 2147483647
  completions: 1
  parallelism: 1
  template:
    spec:
      containers:
        - command:
            - bash
            - -c
            - tail -f /dev/null
          env:
            - name: TF_VAR_security_ips
              value: '"0.0.0.0/0"'
          image: nginx:1.9.4
          imagePullPolicy: IfNotPresent
          name: terraform-executor
      restartPolicy: OnFailure

如果我创建它kubectl apply -f,它会按预期工作。

spec:
  backoffLimit: 2147483647
  completions: 1
  parallelism: 1
  selector:
    matchLabels:
      controller-uid: 1525d501-09f4-419e-8989-eb27ea4ddab5
  template:
    metadata:
      creationTimestamp: null
      labels:
        controller-uid: 1525d501-09f4-419e-8989-eb27ea4ddab5
        job-name: poc
    spec:
      containers:
      - command:
        - bash
        - -c
        - tail -f /dev/null
        env:
        - name: TF_VAR_security_ips
          value: '"0.0.0.0/0"'

如何使 client-go 或 controller-runtime 不生成三个单引号?只需保留单引号的原始数量即可。

4

1 回答 1

2

您从 Go 代码中获得了正确的值,并且只看到了 YAML 序列化工件。

在 YAML 中,字符串可以用单引号或双引号括起来。由于值字符串以引号字符开头,因此必须将其引用,以便可以转义字符串中的引号。序列化器选择了单引号;在单引号字符串中,双单引号''是转义单引号的方法(其他字符不能转义)。

#      v               v start/end of string quoting
value: '''"0.0.0.0/0"'''
#       ^^           ^^  escaped single quotes

您可以等效地使用双引号来执行此操作,它看起来与您的 Go 代码完全一样

#      v             v start/end of string quoting
value: "'\"0.0.0.0\"'"
#        ^^       ^^   escaped double quotes

你后面的例子没有产生相同的字符串。它们是 YAML 单引号字符串,其中包含带双引号但没有单引号的字符串。(试着kubectl exec job/poc -- sh -c 'echo $TF_VAR_security_ips'看看会发生什么。)

于 2021-10-25T11:01:37.680 回答