ConfigMap PropertySource の使用
Kubernetes は、キーと値のペア、または埋め込み application.properties または application.yaml ファイルの形式でアプリケーションに渡すパラメーターを外部化する、ConfigMap (英語) という名前のリソースを提供します。Spring Cloud Kubernetes 構成 [GitHub] (英語) プロジェクトは、アプリケーションの起動時に Kubernetes ConfigMap インスタンスを使用できるようにし、監視されている ConfigMap インスタンスで変更が検出されたときに Bean または Spring コンテキストのホットリロードをトリガーします。
以下の内容は主に ConfigMaps を使用した例を参照して説明されますが、シークレットについても同様です。つまり、すべての機能が両方でサポートされています。
デフォルトの動作では、次のいずれかの metadata.name を持つ Kubernetes ConfigMap に基づいて Fabric8ConfigMapPropertySource (または KubernetesClientConfigMapPropertySource) を作成します。
spring.cloud.kubernetes.config.nameの値Spring アプリケーションの価値 (
spring.application.nameプロパティで定義されているとおり)文字列リテラル
"application"
ただし、複数の ConfigMap インスタンスを使用できる、より高度な構成が可能です。spring.cloud.kubernetes.config.sources リストはこれを可能にします。例: 次の ConfigMap インスタンスを定義できます。
spring:
application:
name: cloud-k8s-app
cloud:
kubernetes:
config:
name: default-name
namespace: default-namespace
sources:
# Spring Cloud Kubernetes looks up a ConfigMap named c1 in namespace default-namespace
- name: c1
# Spring Cloud Kubernetes looks up a ConfigMap named default-name in whatever namespace n2
- namespace: n2
# Spring Cloud Kubernetes looks up a ConfigMap named c3 in namespace n3
- namespace: n3
name: c3 前述の例では、spring.cloud.kubernetes.config.namespace が設定されていない場合、アプリケーションが実行する名前空間で c1 という名前の ConfigMap が検索されます。アプリケーションの名前空間がどのように解決されるかをより深く理解するには、名前空間の解決を参照してください。
一致する ConfigMap が見つかった場合は、次のように処理されます。
個々の構成プロパティを適用します。
spring.application.nameの値によって名前が付けられたプロパティの内容をyaml(またはproperties) として適用します (存在しない場合は、application.yaml/properties)上記の名前と各アクティブなプロファイルの内容をプロパティファイルとして適用します。
例を見てみると、さらにわかりやすいはずです。spring.application.name=my-app であり、k8s という単一のアクティブなプロファイルがあると仮定します。以下のような構成の場合:
kind: ConfigMap
apiVersion: v1
metadata:
name: my-app
data:
my-app.yaml: |-
...
my-app-k8s.yaml: |-
..
my-app-dev.yaml: |-
..
not-my-app.yaml: |-
..
someProp: someValue最終的にロードするものは次のとおりです。
my-app.yamlをファイルとして扱うmy-app-k8s.yamlをファイルとして扱うdevはアクティブなプロファイルではないため、my-app-dev.yamlは無視されましたnot-my-app.yamlはspring.application.nameと一致しないため無視されますsomeProp: someValueプレーンプロパティ
プロパティを読み込む順序は次のとおりです。
最初に
my-app.yamlからすべてのプロパティをロードしますその後、すべてプロファイルベースのソースから:
my-app-k8s.yamlその後、すべてのプレーンプロパティ
someProp: someValue
これは、プロファイルベースのソースが非プロファイルベースのソースより優先されることを意味します (バニラ Spring アプリと同様)。また、プレーンプロパティは、プロファイルベースのソースと非プロファイルベースのソースの両方よりも優先されます。以下に例を示します。
kind: ConfigMap
apiVersion: v1
metadata:
name: my-app
data:
my-app-k8s.yaml: |-
key1=valueA
key2=valueB
my-app.yaml: |-
key1=valueC
key2=valueA
key1: valueD このような ConfigMap を処理すると、プロパティには key1=valueD、key2=valueB が表示されます。
前述のフローの 1 つの例外は、ファイルが YAML またはプロパティファイルであることを示す単一のキーが ConfigMap に含まれる場合です。その場合、キーの名前は application.yaml または application.properties である必要はなく (何でも構いません)、プロパティの値は正しく処理されます。この機能により、次のようなものを使用して ConfigMap が作成されたユースケースが容易になります。
kubectl create configmap game-config --from-file=/path/to/app-config.yaml 次のプロパティを使用してスレッドプール構成を読み取る demo という名前の Spring Boot アプリケーションがあるとします。
pool.size.corepool.size.maximum
これは、次のように yaml 形式で設定マップに外部化できます。
kind: ConfigMap
apiVersion: v1
metadata:
name: demo
data:
pool.size.core: 1
pool.size.max: 16 個々のプロパティはほとんどの場合に問題なく機能します。ただし、場合によっては、組み込み yaml の方が便利です。この場合、次のように、application.yaml という名前の単一プロパティを使用して yaml を埋め込みます。
kind: ConfigMap
apiVersion: v1
metadata:
name: demo
data:
application.yaml: |-
pool:
size:
core: 1
max:16次の例も機能します。
kind: ConfigMap
apiVersion: v1
metadata:
name: demo
data:
custom-name.yaml: |-
pool:
size:
core: 1
max:16ラベルに基づいて検索が行われるように定義することもできます。例:
spring:
application:
name: labeled-configmap-with-prefix
cloud:
kubernetes:
config:
enabled: true
useNameAsPrefix: true
namespace: spring-k8s
sources:
- labels:
letter: a これにより、名前空間 spring-k8s 内でラベル {letter : a} を持つすべての構成マップが検索されます。ここで注意すべき重要な点は、名前で構成マップを読み取る場合とは異なり、複数の構成マップが読み取られる可能性があるということです。通常どおり、同じ機能がシークレットに対してサポートされています。
ConfigMap の読み取り時にマージされるアクティブなプロファイルに応じて、Spring Boot アプリケーションを異なる構成にすることもできます。次のように、application.properties または application.yaml プロパティを使用し、それぞれ独自のドキュメント (--- シーケンスで示される) でプロファイル固有の値を指定することにより、異なるプロファイルに異なるプロパティ値を提供できます。
kind: ConfigMap
apiVersion: v1
metadata:
name: demo
data:
application.yml: |-
greeting:
message: Say Hello to the World
farewell:
message: Say Goodbye
---
spring:
profiles: development
greeting:
message: Say Hello to the Developers
farewell:
message: Say Goodbye to the Developers
---
spring:
profiles: production
greeting:
message: Say Hello to the Ops 前述のケースでは、development プロファイルを使用して Spring アプリケーションにロードされる構成は次のとおりです。
greeting:
message: Say Hello to the Developers
farewell:
message: Say Goodbye to the Developers ただし、production プロファイルがアクティブな場合、構成は次のようになります。
greeting:
message: Say Hello to the Ops
farewell:
message: Say Goodbye 両方のプロファイルがアクティブな場合、ConfigMap 内で最後に表示されるプロパティによって、それより前の値が上書きされます。
もう 1 つのオプションは、プロファイルごとに異なる構成マップを作成することです。spring boot は、アクティブなプロファイルに基づいてそれを自動的に取得します。
kind: ConfigMap
apiVersion: v1
metadata:
name: demo
data:
application.yml: |-
greeting:
message: Say Hello to the World
farewell:
message: Say Goodbyekind: ConfigMap
apiVersion: v1
metadata:
name: demo-development
data:
application.yml: |-
spring:
profiles: development
greeting:
message: Say Hello to the Developers
farewell:
message: Say Goodbye to the Developerskind: ConfigMap
apiVersion: v1
metadata:
name: demo-production
data:
application.yml: |-
spring:
profiles: production
greeting:
message: Say Hello to the Ops
farewell:
message: Say Goodbye どの profile を有効にする必要があるかを Spring Boot に伝えるには、Spring Boot ドキュメントを参照してください。Kubernetes にデプロイするときに特定のプロファイルをアクティブにするオプションの 1 つは、コンテナー仕様で PodSpec で定義できる環境変数を使用して Spring Boot アプリケーションを起動することです。デプロイリソースファイルは次のようになります。
apiVersion: apps/v1
kind: Deployment
metadata:
name: deployment-name
labels:
app: deployment-name
spec:
replicas: 1
selector:
matchLabels:
app: deployment-name
template:
metadata:
labels:
app: deployment-name
spec:
containers:
- name: container-name
image: your-image
env:
- name: SPRING_PROFILES_ACTIVE
value: "development"同じプロパティ名を持つ複数の構成マップが存在する状況が発生する可能性があります。例:
kind: ConfigMap
apiVersion: v1
metadata:
name: config-map-one
data:
application.yml: |-
greeting:
message: Say Hello from oneおよび
kind: ConfigMap
apiVersion: v1
metadata:
name: config-map-two
data:
application.yml: |-
greeting:
message: Say Hello from two これらを bootstrap.yaml|properties に配置する順序によっては、予期しない結果が発生する可能性があります (最後の構成マップが優先されます)。例:
spring:
application:
name: cloud-k8s-app
cloud:
kubernetes:
config:
namespace: default-namespace
sources:
- name: config-map-two
- name: config-map-one プロパティ greetings.message は Say Hello from one になります。
useNameAsPrefix を指定することで、このデフォルト構成を変更する方法があります。例:
spring:
application:
name: with-prefix
cloud:
kubernetes:
config:
useNameAsPrefix: true
namespace: default-namespace
sources:
- name: config-map-one
useNameAsPrefix: false
- name: config-map-twoこのような構成では、次の 2 つのプロパティが生成されます。
greetings.messageはSay Hello from oneに等しい。config-map-two.greetings.messageとSay Hello from twoは等しい
spring.cloud.kubernetes.config.useNameAsPrefix の優先順位は spring.cloud.kubernetes.config.sources.useNameAsPrefix よりも低いことに注意してください。これにより、すべてのソースに対して "default" 戦略を設定できると同時に、いくつかのソースのみをオーバーライドすることができます。
構成マップ名の使用がオプションでない場合は、explicitPrefix という別の戦略を指定できます。これは選択する明示的なプレフィックスであるため、sources レベルにのみ提供できます。同時に、useNameAsPrefix よりも高い優先順位を持ちます。次のエントリを含む 3 番目の構成マップがあるとします。
kind: ConfigMap
apiVersion: v1
metadata:
name: config-map-three
data:
application.yml: |-
greeting:
message: Say Hello from three以下のような構成です。
spring:
application:
name: with-prefix
cloud:
kubernetes:
config:
useNameAsPrefix: true
namespace: default-namespace
sources:
- name: config-map-one
useNameAsPrefix: false
- name: config-map-two
explicitPrefix: two
- name: config-map-threeその結果、次の 3 つのプロパティが生成されます。
greetings.messageはSay Hello from oneに等しい。two.greetings.messageはSay Hello from twoに等しい。config-map-three.greetings.messageはSay Hello from threeに等しい。
configmap のプレフィックスを設定するのと同じ方法で、シークレットに対しても行うことができます。名前に基づくシークレットとラベルに基づくシークレットの両方。例:
spring:
application:
name: prefix-based-secrets
cloud:
kubernetes:
secrets:
enabled: true
useNameAsPrefix: true
namespace: spring-k8s
sources:
- labels:
letter: a
useNameAsPrefix: false
- labels:
letter: b
explicitPrefix: two
- labels:
letter: c
- labels:
letter: d
useNameAsPrefix: true
- name: my-secret プロパティソースを生成する際にも、設定マップと同じ処理ルールが適用されます。唯一の違いは、ラベルでシークレットを検索すると、複数のソースが見つかる可能性があることです。そのような場合、プレフィックス(useNameAsPrefix で指定されている場合)は、それらのラベルで見つかったシークレットの名前になります。
もう 1 つ覚えておいていただきたいのは、シークレットごとに prefix をサポートしていることです。これを最も簡単に説明するには、例を挙げましょう。
spring:
application:
name: prefix-based-secrets
cloud:
kubernetes:
secrets:
enabled: true
useNameAsPrefix: true
namespace: spring-k8s
sources:
- labels:
color: blue
useNameAsPrefix: true このようなラベルに一致するクエリが、結果として 2 つのシークレット(secretA と secretB)を返すとします。これらのシークレットはどちらも同じプロパティ名(color=sea-blue と color=ocean-blue)を持ちます。useNamesAsPrefix=true であるため、2 つのプロパティソースがロードされます。
secretA.color=sea-bluesecretB.color=ocean-blue
デフォルトでは、sources 構成で指定された構成マップを読み取るほかに、Spring は「プロファイル対応」ソースからすべてのプロパティを読み取ろうとします。これを説明する最も簡単な方法は、例を使用することです。アプリケーションで "dev" というプロファイルが有効になっており、次のような構成があるとします。
spring:
application:
name: spring-k8s
cloud:
kubernetes:
config:
namespace: default-namespace
sources:
- name: config-map-oneSpring は config-map-one の読み取りに加えて、config-map-one-dev の読み取りもこの特定の順序で試みます。アクティブなプロファイルごとに、このようなプロファイル対応の設定マップが生成されます。
この「プロファイルベースのソース」を無効にすると、config-map-one-dev は試行されなくなります。
spring:
application:
name: spring-k8s
cloud:
kubernetes:
config:
includeProfileSpecificSources: false
namespace: default-namespace
sources:
- name: config-map-one
includeProfileSpecificSources: false バージョン 5.0.0 以降、includeProfileSpecificSources は名前付きソース (spring.cloud.kubernetes.sources.name=XXX) に対してのみサポートされ、ラベル付きソースのサポートは削除されました。 |
以前と同様に、このプロパティを指定できるレベルは 2 つあります。つまり、すべての構成マップに対して、または個別の構成マップに対してです。後者の方が優先されます。
| セキュリティ構成セクションを確認する必要があります。pod 内から構成マップにアクセスするには、正しい Kubernetes サービスアカウント、ロール、ロールバインディングが必要です。 |
場合によっては、アプリケーションが Kubernetes API を使用して ConfigMaps の一部をロードできないことがあります。このような場合にアプリケーションが起動プロセスに失敗するようにしたい場合は、アプリケーションの起動が例外で失敗するように spring.cloud.kubernetes.config.fail-fast=true を設定できます。
失敗した場合に、アプリケーションで ConfigMap プロパティソースのロードを再試行するようにすることもできます。まず、spring.cloud.kubernetes.config.fail-fast=true を設定する必要があります。次に、spring-retry と spring-boot-starter-aspectj をクラスパスに追加する必要があります。spring.cloud.kubernetes.config.retry.* プロパティを設定することで、最大試行回数、初期間隔、乗数、最大間隔などのバックオフオプションなどの再試行プロパティを構成できます。
何らかの理由ですでにクラスパス上に spring-retry および spring-boot-starter-aspectj があり、フェイルファストを有効にしたいが、再試行は有効にしたくない場合。spring.cloud.kubernetes.config.retry.enabled=false を設定することで、ConfigMap PropertySources の再試行を無効にできます。 |
バージョン 5.0.0 以降、ソースを個別に読み取る機能を導入しました。これまでは、名前空間にアクセスし、利用可能なすべての configmaps/secrets を読み取り、リクエストされたものをフィルタリングしていました。5.0.0-M3 以降では、プロパティ spring.cloud.kubernetes.config.read-type=SINGLE を設定することで、個別に読み取るように指定できます。名前空間内のすべての configmaps/secrets を読み取る以前のオプションは、spring.cloud.kubernetes.config.read-type=BATCH によって制御され、これがデフォルトオプションとなっています。 |
| 名前 | タイプ | デフォルト | 説明 |
|---|---|---|---|
|
|
| ConfigMaps |
|
|
| 検索する |
|
| クライアント名前空間 | ルックアップ先の Kubernetes 名前空間を設定します |
|
|
|
|
|
|
| 構成の再試行を有効または無効にします。 |
|
|
| ミリ秒単位の初期再試行間隔。 |
|
|
| 最大試行回数。 |
|
|
| バックオフの最大間隔。 |
|
|
| 次の区間の乗数。 |