본문 바로가기

개발하자

어떻게 yaml에 의해 비밀 파일을 쿠버네티스 비밀로 설정합니까?

반응형

어떻게 yaml에 의해 비밀 파일을 쿠버네티스 비밀로 설정합니까?

나는 Kubernetes Secrets에 파일을 저장하고 싶지만 파일을 사용하는 방법을 찾지 못했다.

나는 다음과 같은 cli를 사용하여 그것을 만들 수 있었다:

kubectl create secret generic some-secret --from-file=secret1.txt=secrets/secret1.txt

하지만 내가 a에서 비슷한 것을 시도할 때:

apiVersion: v1
kind: Secret
metadata:
  name: some-secret
type: Opaque
data:
  secret1.txt: secrets/secret1.txt

다음 오류가 발생했습니다:

[pos 73]: json: error decoding base64 binary 'assets/elasticsearch.yml': illegal base64 data at input byte 20

저는 이 가이드를 따르고 있습니다. 그것은 을 사용하여 비밀을 만드는 방법을 설명하지만 을 사용하여 비밀을 만드는 방법은 설명하지 않는다.

가능합니까? 그렇다면 어떻게 해야 할까요?




이전 게시물에서 답변한 것처럼, 우리는 64 기반으로 인코딩된 인증서/키를 파일에 제공해야 합니다.

다음은 인증서의 일반적인 예입니다(이 경우 SSL):

대상:

    apiVersion: v1    

    kind: Secret
    metadata:
         name: test-secret
         namespace: default
    type: Opaque
    data:
        server.crt: SERVER_CRT
        server.key: SERVER_KEY

인증서/키를 포함하도록 파일을 사전 처리합니다:

sed "s/SERVER_CRT/`cat server.crt|base64 -w0`/g" secret.yml.tmpl | \
sed "s/SERVER_KEY/`cat server.key|base64 -w0`/g" | \
kubectl apply -f -

인증서/키는 공백(-w0) 없이 base64를 사용하여 인코딩됩니다.

TLS의 경우 다음과 같을 수 있습니다:

kubectl create secret tls test-secret-tls --cert=server.crt --key=server.key



형식을 사용할 때 서버 측에 게시하기 전에 YAML의 생성기를 사용합니다.

쿠버네티스는 REST API를 사용하는 클라이언트-서버 앱이며, 모든 동작이 원자적이어야 하기 때문에 게시된 YAML은 링크된 파일의 내용을 포함해야 하며, 이를 위한 최선의 방법은 base64 인코딩된 형식(인라인)에 포함시키는 것이다. 파일이 다른 방식으로 내장될 수 있다면 좋겠지만(삽입을 사용하여 파일의 경계를 만들 수도 있음), 나는 그것에 대한 작업 예를 본 적이 없다.

그럼에도 불구하고, YAML에 파일 참조를 넣는 것은 불가능하며, 내용을 포함하기 위한 YAML의 비행 전 렌더링은 없다.




회의실에 있는 윈도우즈 사용자의 경우 .cer 및 .key 각각에 대해 다음을 사용합니다(예를 들어 .key가 YAML 파일에 삽입되도록 인코딩되어 있음):

$Content = Get-Content -Raw -Path C:\ssl-cert-decrypted.key

[Convert]::ToBase64String([System.Text.Encoding]::UTF8.GetBytes($Content)) | Out-File -FilePath C:\ssl-cert-decrypted.key.b64

새 파일을 열고 (한 줄) 출력을 YAML 파일에 붙여 넣으십시오. 이 정보가 들어 있는 소스 코드 레포에 YAML 파일을 체크인하면 base64가 암호화가 아니기 때문에 키가 효과적으로 손상될 수 있습니다.




를 사용하여 암호화된 문자열로 암호화된 값을 바꿀 수 있습니다:

secode secrets.yaml > secrets_base64.yaml

모든 필드를 인코딩하며 목록에 정의된 경우 파일당 여러 개의 비밀()로 작동합니다.

고지 사항: 내가 작가다




그래서 저는 제가 놓쳤던 매우 유용한 k8s 기본 사항을 알게 되었고, 그와 관련된 보안 취약점이 있다는 것을 발견하고 해결책을 생각해냈습니다.

(참고로 이것을 Hashicorp Vault에 저장하는 것을 추천합니다. 비밀번호가 있는 버전의 구성 파일을 저장하고 볼트 웹페이지를 통해 쉽게 보거나 편집할 수 있으며, gitrepo와 달리 세부적인 액세스 제어가 가능하며, 파이프라인은 REST API를 사용하여 업데이트된 비밀번호를 풀어서 암호를 쉽게 회전할 수 있습니다.)

앱 설정.Dummy.json은 기본 파일 이름(비밀 키)이며(yaml 마운트에서 재정의할 수 있는 기본 파일 이름이라는 단어를 사용합니다), 클리어 텍스트 json 코드는 파일 내용(비밀의 값)입니다

apiVersion: v1
kind: Secret
metadata:
  name: appsettings
  namespace: api
type: Opaque
stringData:
  appsettings.Dummy.json: |-
    {
      "Dummy": {
        "Placeholder": {
          "Password": "blank"
        }
      }
    }

주석에 비밀이 표시되면...

apiVersion: v1
data:
  appsettings.Dummy.json: ewogICJEdW1teSI6IHsKICAgICJQbGFjZWhvbGRlciI6IHsKICAgICAgIlBhc3N3b3JkIjogImJsYW5rIgogICAgfQogIH0KfQ==
kind: Secret
metadata:
  annotations:
    kubectl.kubernetes.io/last-applied-configuration: |
      {"apiVersion":"v1","kind":"Secret","metadata":{"annotations":{},"name":"appsettings","namespace":"api"},"stringData":{"appsettings.Dummy.json":"{\n  \"Dummy\": {\n    \"Placeholder\": {\n      \"Password\": \"blank\"\n    }\n  }\n}"},"type":"Opaque"}
  creationTimestamp: 2019-01-31T02:50:16Z
  name: appsettings
  namespace: api
  resourceVersion: "4909"
  selfLink: /api/v1/namespaces/api/secrets/appsettings
  uid: f0629027-2502-11e9-9375-6eb4e0983acc

분명히 주석에 나타나는 비밀을 만드는 데 사용된 yaml은 kubectl apply -f secret.yaml에 대한 예상 동작입니다./ 2016년부터 버그 보고서로 게시되었지만 해결되지 않고 문제가 종료되었습니다./ 그들은 그것을 무시하고 있습니다.

만약 당신이 원래 secret.yaml is base64'd라면 주석은 적어도 base64'가 될 것이지만, 이 시나리오에서 그것은 인간이 읽을 수 있는 non-base64'd 클리어 텍스트이다.

참고 1: 필수 비밀 생성 kubectl 비밀 일반 앱 설정 - from-file 앱 설정에서는 발생하지 않습니다.Dummy.json --dummy=api

참고 2: 선언적 appsettings-secret.yaml을 선호하는 또 다른 이유는 kubectl apply -f가 비밀을 구성하지만, 만약 당신이 그 create 명령어를 실행한다면 그것은 이미 오류가 있다고 말할 것이고 당신은 그것을 삭제해야만 당신이 다시 create 명령어를 실행할 수 있기 때문이다.

참고 3: kubectl이 비밀 일반 이름을 만드는 이유 --from-file 파일 --namespace / secret.yaml에 반대하는 이유는 비밀이 마지막으로 편집되었을 때 kubectl show secret이 표시되지 않기 때문입니다. create 명령과 마찬가지로 create 명령을 다시 생성하려면 먼저 삭제해야 하므로 해당 명령이 존재한 기간에 따라 마지막으로 편집된 시간을 알 수 있으므로 감사 평가판에 적합합니다. (그러나 더 나은 감사 방법이 있습니다.)

누출을 방지합니다

apiVersion: v1
data:
  appsettings.Dummy.json: ewogICJEdW1teSI6IHsKICAgICJQbGFjZWhvbGRlciI6IHsKICAgICAgIlBhc3N3b3JkIjogImJsYW5rIgogICAgfQogIH0KfQ==
kind: Secret
metadata:
  creationTimestamp: 2019-01-31T03:06:55Z
  name: appsettings
  namespace: api
  resourceVersion: "6040"
  selfLink: /api/v1/namespaces/api/secrets/appsettings
  uid: 43f1b81c-2505-11e9-9375-6eb4e0983acc
type: Opaque



--dry-run 플래그를 사용하여 파일의 데이터를 포함하는 YAML을 준비할 수 있습니다.

kubectl create secret generic jwt-certificates --from-file=jwt-public.cer --from-file=jwt-private.pfx --dry-run=true  --output=yaml > jwt-secrets.yaml

편집

API 사용 중지에 대한 @Leopd의 의견 덕분에 new kubectl은 다음 명령을 사용합니다:

kubectl create secret generic jwt-certificates --from-file=jwt-public.cer --from-file=jwt-private.pfx --dry-run=client --output=yaml > jwt-secrets.yaml

내 기계에는 여전히 오래된 쿠벡틀 버전이 있다


반응형