Как создать секрет кубернетов как объект json и загрузить его в среду кубернетов как json - PullRequest
0 голосов
/ 28 мая 2020

Мне нужно передать JWK как переменную среды kubernetes моему приложению.

Я создал файл для хранения моего ключа следующим образом:

cat deploy/keys/access-signature-public-jwk 
{
  algorithm = "RS256"
  jwk = {"kty":"RSA","e":"AQAB","n":"ghhDZxuUo6TaSvAlD23mLP6n_T9pQuJsFY4JWdBYTjtcp_8Q3QeR477jou4cScPGczWw2JMGnx-Ao_b7ewagSl7VHpECBFHgcnlAgs5j6jfnd3M9ADKD2Yc756iXlIMT9xKDblIcXQQYlXalqxGvnLRLv1KAgVVVpVWzQd6Iz8WdTnexVrh7L9N87QQbOWcAVWGHCWCLCBsVE7JbC-XDt9h9P1g1sMqMV-qp7HjSXUKWuF2NwOnL2VeFSED7gdefs2Za1UYqhfwxdGl7aaPDXhjib0cfg4NvbcXMzxDEVkeJqhdDfD82wHOs4qFvnFMVxq9n6VVExSxsJq8gBJ7Z2AmfoXpmZC1L1ZwULB2KKpFXDCzgBELPLrfyIf8mNnk2nuuLT-aaMsqy2uB-ea3du4lyWo9MLk6x-L5g-n1oADKFKBY9aP2QQwruCG92XSd7jA9yLtbgr9OGVCYezxIxFp4vW6KcmPwJQjozWtwkZjeo4hv-zhRac73WDox2hDkif7WPTuEvC21fRy3GvyPIUPKPJA8pJjb2TXT7DXknR97CTnOWicuh3HMoRlVIwUzM5SVLGSXex0VjHZKgLYwQYukg5O2rab_4NxpD6LqLHx1bbPssC7BedCIfWX1Vcae40tlfvJAM09MiwQPZjWRahW_fK_9X5F5_rtUhCznm32M"}
}

который затем используется для создания kubernetes secret следующим образом:

kubectl create secret generic intimations-signature-public-secret --from-file=./deploy/keys/access-signature-public-jwk

, который затем извлекается в переменной среды kubernetes как:

- name: ACCESS_SIGNATURE_PUBLIC_JWK
  valueFrom:
    secretKeyRef:
      name: intimations-signature-public-secret
      key: access-signature-public-jwk

и передается в application.conf приложения likeo:

pac4j.lagom.jwt.authenticator {
  signatures = [
    ${ACCESS_SIGNATURE_PUBLIC_JWK}
  ]
}

Библиотека pac4j ожидает конфигурацию pac4j.lagom.jwt.authenticator как объект json. Но когда я запускаю это приложение, получаю следующее исключение:

com.typesafe.config.ConfigException$WrongType: env variables: signatures has type list of STRING rather than list of OBJECT
    at com.typesafe.config.impl.SimpleConfig.getHomogeneousWrappedList(SimpleConfig.java:452)
    at com.typesafe.config.impl.SimpleConfig.getObjectList(SimpleConfig.java:460)
    at com.typesafe.config.impl.SimpleConfig.getConfigList(SimpleConfig.java:465)
    at org.pac4j.lagom.jwt.JwtAuthenticatorHelper.parse(JwtAuthenticatorHelper.java:84)
    at com.codingkapoor.holiday.impl.core.HolidayApplication.jwtClient$lzycompute(HolidayApplication.scala

Описание POD

Name:         holiday-deployment-55b86f955d-9klk2
Namespace:    default
Priority:     0
Node:         minikube/192.168.99.103
Start Time:   Thu, 28 May 2020 12:42:50 +0530
Labels:       app=holiday
              pod-template-hash=55b86f955d
Annotations:  <none>
Status:       Running
IP:           172.17.0.5
IPs:
  IP:           172.17.0.5
Controlled By:  ReplicaSet/holiday-deployment-55b86f955d
Containers:
  holiday:
    Container ID:   docker://18443cfedc7fd39440f5fa6f038f36c58cec1660a2974e6432500e8c7d51f5e6
    Image:          codingkapoor/holiday-impl:latest
    Image ID:       docker://sha256:6e0ddcf41e0257755b7e865424671970091d555c4bad88b5d896708ded139eb7
    Port:           8558/TCP
    Host Port:      0/TCP
    State:          Terminated
      Reason:       Error
      Exit Code:    255
      Started:      Thu, 28 May 2020 22:49:24 +0530
      Finished:     Thu, 28 May 2020 22:49:29 +0530
    Last State:     Terminated
      Reason:       Error
      Exit Code:    255
      Started:      Thu, 28 May 2020 22:44:15 +0530
      Finished:     Thu, 28 May 2020 22:44:21 +0530
    Ready:          False
    Restart Count:  55
    Liveness:       http-get http://:management/alive delay=20s timeout=1s period=10s #success=1 #failure=10
    Readiness:      http-get http://:management/ready delay=20s timeout=1s period=10s #success=1 #failure=10
    Environment:
      JAVA_OPTS:                     -Xms256m -Xmx256m -Dconfig.resource=prod-application.conf
      APPLICATION_SECRET:            <set to the key 'secret' in secret 'intimations-application-secret'>  Optional: false
      MYSQL_URL:                     jdbc:mysql://mysql/intimations_holiday_schema
      MYSQL_USERNAME:                <set to the key 'username' in secret 'intimations-mysql-secret'>                                 Optional: false
      MYSQL_PASSWORD:                <set to the key 'password' in secret 'intimations-mysql-secret'>                                 Optional: false
      ACCESS_SIGNATURE_PUBLIC_JWK:   <set to the key 'access-signature-public-jwk' in secret 'intimations-signature-public-secret'>   Optional: false
      REFRESH_SIGNATURE_PUBLIC_JWK:  <set to the key 'refresh-signature-public-jwk' in secret 'intimations-signature-public-secret'>  Optional: false
      REQUIRED_CONTACT_POINT_NR:     1
    Mounts:
      /var/run/secrets/kubernetes.io/serviceaccount from default-token-kqmmv (ro)
Conditions:
  Type              Status
  Initialized       True 
  Ready             False 
  ContainersReady   False 
  PodScheduled      True 
Volumes:
  default-token-kqmmv:
    Type:        Secret (a volume populated by a Secret)
    SecretName:  default-token-kqmmv
    Optional:    false
QoS Class:       BestEffort
Node-Selectors:  <none>
Tolerations:     node.kubernetes.io/not-ready:NoExecute for 300s
                 node.kubernetes.io/unreachable:NoExecute for 300s
Events:
  Type     Reason   Age                    From               Message
  ----     ------   ----                   ----               -------
  Normal   Pulled   5m21s (x23 over 100m)  kubelet, minikube  Container image "codingkapoor/holiday-impl:latest" already present on machine
  Warning  BackOff  27s (x466 over 100m)   kubelet, minikube  Back-off restarting failed container

Мне было интересно, есть ли способ передать переменную среды как объект json вместо строки. Пожалуйста, предложите. TIA.

Ответы [ 2 ]

2 голосов
/ 28 мая 2020

Во-первых, файл access-signature-public-jwk не является допустимым файлом JSON. Вы должны обновить его как действительный.

{
  "algorithm" : "RS256",
  "jwk" : {"kty":"RSA","e":"AQAB","n":"ghhDZxuUo6TaSvAlD23mLP6n_T9pQuJsFY4JWdBYTjtcp_8Q3QeR477jou4cScPGczWw2JMGnx-Ao_b7ewagSl7VHpECBFHgcnlAgs5j6jfnd3M9ADKD2Yc756iXlIMT9xKDblIcXQQYlXalqxGvnLRLv1KAgVVVpVWzQd6Iz8WdTnexVrh7L9N87QQbOWcAVWGHCWCLCBsVE7JbC-XDt9h9P1g1sMqMV-qp7HjSXUKWuF2NwOnL2VeFSED7gdefs2Za1UYqhfwxdGl7aaPDXhjib0cfg4NvbcXMzxDEVkeJqhdDfD82wHOs4qFvnFMVxq9n6VVExSxsJq8gBJ7Z2AmfoXpmZC1L1ZwULB2KKpFXDCzgBELPLrfyIf8mNnk2nuuLT-aaMsqy2uB-ea3du4lyWo9MLk6x-L5g-n1oADKFKBY9aP2QQwruCG92XSd7jA9yLtbgr9OGVCYezxIxFp4vW6KcmPwJQjozWtwkZjeo4hv-zhRac73WDox2hDkif7WPTuEvC21fRy3GvyPIUPKPJA8pJjb2TXT7DXknR97CTnOWicuh3HMoRlVIwUzM5SVLGSXex0VjHZKgLYwQYukg5O2rab_4NxpD6LqLHx1bbPssC7BedCIfWX1Vcae40tlfvJAM09MiwQPZjWRahW_fK_9X5F5_rtUhCznm32M"}
}

Шаги, которые я выполнил для проверки.

kubectl create secret generic token1 --from-file=jwk.json

Установите секрет в модуль.

env:
  - name: JWK
    valueFrom:
      secretKeyRef:
        name: token
        key: jwk.json

exec в модуль и проверьте переменную env JWK

$ echo $JWK
{ "algorithm" : "RS256", "jwk" : {"kty":"RSA","e":"AQAB","n":"ghhDZxuUo6TaSvAlD23mLP6n_T9pQuJsFY4JWdBYTjtcp_8Q3QeR477jou4cScPGczWw2JMGnx-Ao_b7ewagSl7VHpECBFHgcnlAgs5j6jfnd3M9ADKD2Yc756iXlIMT9xKDblIcXQQYlXalqxGvnLRLv1KAgVVVpVWzQd6Iz8WdTnexVrh7L9N87QQbOWcAVWGHCWCLCBsVE7JbC-XDt9h9P1g1sMqMV-qp7HjSXUKWuF2NwOnL2VeFSED7gdefs2Za1UYqhfwxdGl7aaPDXhjib0cfg4NvbcXMzxDEVkeJqhdDfD82wHOs4qFvnFMVxq9n6VVExSxsJq8gBJ7Z2AmfoXpmZC1L1ZwULB2KKpFXDCzgBELPLrfyIf8mNnk2nuuLT-aaMsqy2uB-ea3du4lyWo9MLk6x-L5g-n1oADKFKBY9aP2QQwruCG92XSd7jA9yLtbgr9OGVCYezxIxFp4vW6KcmPwJQjozWtwkZjeo4hv-zhRac73WDox2hDkif7WPTuEvC21fRy3GvyPIUPKPJA8pJjb2TXT7DXknR97CTnOWicuh3HMoRlVIwUzM5SVLGSXex0VjHZKgLYwQYukg5O2rab_4NxpD6LqLHx1bbPssC7BedCIfWX1Vcae40tlfvJAM09MiwQPZjWRahW_fK_9X5F5_rtUhCznm32M"} }

Скопируйте содержимое в файл

echo $JWK > jwk.json

Подтвердите файл

$ jsonlint-php jwk.json 
Valid JSON (jwk.json)

Если я использую предоставленный вам файл и выполняю те же действия. Выдает ошибку проверки json. Кроме того, переменные env всегда являются строками. Вы должны преобразовать их в требуемые типы в своем коде.

$ echo $JWK
{ algorithm = "RS256" jwk = {"kty":"RSA","e":"AQAB","n":"ghhDZxuUo6TaSvAlD23mLP6n_T9pQuJsFY4JWdBYTjtcp_8Q3QeR477jou4cScPGczWw2JMGnx-Ao_b7ewagSl7VHpECBFHgcnlAgs5j6jfnd3M9ADKD2Yc756iXlIMT9xKDblIcXQQYlXalqxGvnLRLv1KAgVVVpVWzQd6Iz8WdTnexVrh7L9N87QQbOWcAVWGHCWCLCBsVE7JbC-XDt9h9P1g1sMqMV-qp7HjSXUKWuF2NwOnL2VeFSED7gdefs2Za1UYqhfwxdGl7aaPDXhjib0cfg4NvbcXMzxDEVkeJqhdDfD82wHOs4qFvnFMVxq9n6VVExSxsJq8gBJ7Z2AmfoXpmZC1L1ZwULB2KKpFXDCzgBELPLrfyIf8mNnk2nuuLT-aaMsqy2uB-ea3du4lyWo9MLk6x-L5g-n1oADKFKBY9aP2QQwruCG92XSd7jA9yLtbgr9OGVCYezxIxFp4vW6KcmPwJQjozWtwkZjeo4hv-zhRac73WDox2hDkif7WPTuEvC21fRy3GvyPIUPKPJA8pJjb2TXT7DXknR97CTnOWicuh3HMoRlVIwUzM5SVLGSXex0VjHZKgLYwQYukg5O2rab_4NxpD6LqLHx1bbPssC7BedCIfWX1Vcae40tlfvJAM09MiwQPZjWRahW_fK_9X5F5_rtUhCznm32M"} }
$ echo $JWK > jwk.json
$ jsonlint-php jwk.json 
jwk.json: Parse error on line 1:
{ algorithm = "RS256" 
-^
Expected one of: 'STRING', '}'
1 голос
/ 29 мая 2020

Хотя это и не прямой ответ, но альтернативное решение этой проблемы.

Как отметил @hariK, переменные среды всегда являются строками, и для того, чтобы использовать их как json, нам нужно будет преобразовать env var читать как строку в json.

Однако в моем случае это не было жизнеспособным решением, потому что я использовал библиотеку, которая ожидала объект Config , а не json объект напрямую, что потребовало бы много работы. Преобразование string -> json -> Config. Кроме того, этот подход несовместим с тем, как объект Config создавался в сценарии разработки ios, то есть json -> Config. См. здесь .

Фреймворк, который я использую для создания этого приложения, основан на Play Framework , который позволяет разбивать конфигурации приложений на модули в отдельных файлах, а затем объединять необходимые части вместе в желаемом файле конфигурации, как показано ниже. Вы можете прочитать его более подробно здесь .

application.conf

include "/opt/conf/app1.conf"
include "/opt/conf/app2.conf"

Это позволило мне использовать Используя Секреты в виде файлов из функции Pod от kubernetes.

  1. По сути, я создал небольшой файл конфигурации, который содержит часть моего основного файла конфигурации приложения, как показано ниже:
cat deploy/keys/signature-public-jwk 
pac4j.lagom.jwt.authenticator {
  signatures = [
    {
      algorithm = "RS256"
      jwk = {"kty":"RSA","e":"AQAB","n":"ghhDZxuUo6TaSvAlD23mLP6n_T9pQuJsFY4JWdBYTjtcp_8Q3QeR477jou4cScPGczWw2JMGnx-Ao_b7ewagSl7VHpECBFHgcnlAgs5j6jfnd3M9ADKD2Yc756iXlIMT9xKDblIcXQQYlXalqxGvnLRLv1KAgVVVpVWzQd6Iz8WdTnexVrh7L9N87QQbOWcAVWGHCWCLCBsVE7JbC-XDt9h9P1g1sMqMV-qp7HjSXUKWuF2NwOnL2VeFSED7gdefs2Za1UYqhfwxdGl7aaPDXhjib0cfg4NvbcXMzxDEVkeJqhdDfD82wHOs4qFvnFMVxq9n6VVExSxsJq8gBJ7Z2AmfoXpmZC1L1ZwULB2KKpFXDCzgBELPLrfyIf8mNnk2nuuLT-aaMsqy2uB-ea3du4lyWo9MLk6x-L5g-n1oADKFKBY9aP2QQwruCG92XSd7jA9yLtbgr9OGVCYezxIxFp4vW6KcmPwJQjozWtwkZjeo4hv-zhRac73WDox2hDkif7WPTuEvC21fRy3GvyPIUPKPJA8pJjb2TXT7DXknR97CTnOWicuh3HMoRlVIwUzM5SVLGSXex0VjHZKgLYwQYukg5O2rab_4NxpD6LqLHx1bbPssC7BedCIfWX1Vcae40tlfvJAM09MiwQPZjWRahW_fK_9X5F5_rtUhCznm32M"}
    }
  ]
}
Затем создал секрет кубернетов и примонтировал тома при развертывании, чтобы они отображались в модуле в виде файла
kubectl create secret generic signature-public-secret --from-file=./deploy/secrets/signature-public-jwks.conf

// deployment yaml
    spec:
      containers:
        - name: employee
          image: "codingkapoor/employee-impl:latest"
          volumeMounts:
            - name: signature-public-secret-conf
              mountPath: /opt/conf/signature-public-jwks.conf
              subPath: signature-public-jwks.conf
              readOnly: true
      volumes:
        - name: signature-public-secret-conf
          secret:
            secretName: signature-public-secret
Используйте это место смонтированного файла в application.conf, чтобы включить тот же
include file("/opt/conf/signature-public-jwks.conf")

Обратите внимание, что mountPath и расположение файла в application.conf совпадают.

Преимущества этого подхода:

  1. Решение совместимо с рабочей средой разработки и тестирования, поскольку мы могли бы вернуть json вместо строки в библиотеку, как описано выше.

  2. Секреты в любом случае не должны передаваться как переменные среды! Подробнее об этом можно прочитать здесь .

...