Next.js アプリの Helm チャート
charts/<app>/ と、Argo CD がそれをどのように使用するかについて説明します。実行されるイメージは docker-nextjs から提供され、両方を公開するパイプラインは github-actions です。
テンプレートの charts/__APP__/ が信頼できる情報源です。コメント付きのすべての値: references/values.md。Argo CD の配線: references/argocd.md。
ルール
-
アプリごとに 1 つのチャートを、アプリのリポジトリルートの
charts/<app>/に配置します。 その理由: Argo CD は開発環境では Git から (path: charts/<app>) 直接同期でき、本番環境では OCI レジストリから同じファイルで同期できます。apps/の外にあるため、Docker ビルドコンテキストにも pnpm ワークスペースパッケージにも含まれません。また、チャートの変更は、それを必要とするコードと同じ PR で行われます。チャートは意図的にシングルアプリであり、アンブレラチャートやサブチャートはありません。汎用的で値駆動型のテンプレート (バックエンドアンブレラチャートなど) は、単一のアプリが Ingress、HPA、PDB、トポロジースプレッドなどのスイッチを必要とする場合にのみ使用します。 -
versionまたはappVersionを手動で編集しないでください。 両方とも Git では0.0.0のままにします。release.yamlはタグvX.Y.Zからhelm package --version X.Y.Z --app-version vX.Y.Zを実行するため、公開されたチャートとイメージタグは常に一致します。 -
image.tagはデフォルトでappVersionになります。Git 同期環境でのみ設定します。 OCI からは、appVersionがリリースタグであり、イメージはghcr.io/nuvraxis/<app>:vX.Y.Zです。Git から同期する場合、appVersionは0.0.0であるため、Argo CD Application はimage.tag: sha-<short-sha>(またはmain) を設定します。image.repositoryは常に小文字です。 -
プローブ: startup、liveness、readiness、すべて
/api/healthを使用します。 startup プローブ (2秒 × 30) は起動をカバーし、liveness と readiness はその後にのみ開始されます。このルートは依存関係にまったく触れないため、データベースの障害でポッドが再起動されることはありません。プローブを/に向けないでください: ページがレンダリングされます。 -
セキュリティコンテキストはイメージと一致します: uid/gid 1001、
runAsNonRoot、readOnlyRootFilesystem、権限昇格なし、すべてのケーパビリティをドロップ、RuntimeDefaultseccomp。 ServiceAccount とポッドの両方でautomountServiceAccountToken: falseにします。アプリは Kubernetes API を呼び出しません。 -
.next/cacheはsizeLimit付きのemptyDirです。 これは唯一の書き込み可能パス (/app/apps/<app>/.next/cache) です。制限により、暴走したイメージキャッシュがノードを満杯にするのを防ぎます。 -
envFromによる設定:values.configからの ConfigMap と、既に存在する Secret。config: API_BASE_URL: https://api.nuvraxis.com existingSecret: portal-secretsチャートは Secret の値をテンプレート化しません:
kind: Secretと値からのdata、--set secret=…はありません。Secret は External Secrets、Sealed Secrets、またはオペレーターによって作成され、その名前のみが値に含まれます。ConfigMap の変更は、checksum/configアノテーションを通じてポッドをロールアウトします。 -
チャートに
NEXT_PUBLIC_*は含めません。 これらはイメージビルド時に焼き付けられます (docker-nextjsを参照)。実行時に設定しても何も効果がありません。 -
リソース: CPU とメモリのリクエスト、メモリ制限、CPU 制限なし。 CPU 制限は、バースト中に Node サーバーをスロットルし、テールレイテンシを増加させます。メモリ制限は、Node のヒープが与えられたものに成長するため、そのまま残します。
-
デフォルトで高可用性: 2 レプリカ、PDB
maxUnavailable: 1、maxUnavailable: 0のローリングアップデート、ゾーンとノード間のトポロジースプレッド (ScheduleAnyway)。autoscaling.enabledが有効な場合、Deployment はreplicasを省略するため、Argo CD と HPA が競合しません。 -
Ingress はオプトイン、TLS は cert-manager アノテーションを使用します。
ingress.enabled、className、hosts、secretNameを持つtls、およびアノテーション内のcert-manager.io/cluster-issuer。ingress-nginx でストリーミング応答を行うには、nginx.ingress.kubernetes.io/proxy-buffering: "off"を追加します。レート制限には、limit-rpsを使用します (nextjs-securityを参照)。 -
Helm フック、
lookup、ランダム値は使用しません。 Argo CD はhelm templateでチャートをレンダリングし、その結果を適用します。フックは Argo CD では異なるセマンティクスのフックになり、lookupは何も返さず、randAlphaNumは同期のたびに変更され、アプリを恒久的に同期状態から外します。レンダリングされるものはすべて、値の純粋関数でなければなりません。 -
プライベート GHCR パッケージにはプル資格情報が必要です。 GHCR パッケージは最初のプッシュ時にはプライベートです。イメージの場合:
read:packages権限を持つトークンを含むdocker-registrySecret をimagePullSecretsで参照します (本番値はghcr-pullを参照)。Argo CD のチャートの場合:enableOCI: "true"を持つリポジトリ Secret を使用します (references/argocd.mdを参照)。または、コードが公開されている場合は、GitHub でパッケージを公開にします。 -
values-production.yamlには、本番環境で異なるもののみを保持します。 レイヤー化:-f values.yaml -f values-production.yaml。デフォルトをコピーしないでください。 -
helm lint --strictとhelm template | kubeconform -strictで検証します。 helm-unittest ではなく kubeconform を使用する理由: シングルアプリチャートが実際に持つバグは、レンダリング出力のフィールド名、タイプ、API バージョンの誤りであり、kubeconform は実際の Kubernetes スキーマに対して、テストコードなしでこれらをキャッチします。helm-unittest はテンプレートロジックをアサートしますが、このチャートにはほとんどありません。pr.yamlと同様に、両方の値ファイルに対して lint と検証を実行します。
追加項目
| 必要なもの | 変更内容 |
|---|---|
| ランタイム環境変数 | 値の config: (非シークレット) または既存の Secret のキー |
| シークレット | 外部 Secret に追加。チャートは変更なし |
| 別のポートまたはサイドカー | 最初に正当化。Next アプリには 1 ポート必要 |
| スケジュールジョブ | この Deployment ではなく、別のチャートまたはアプリ |
| NetworkPolicy | templates/networkpolicy.yaml を追加、networkPolicy.enabled で切り替え |
検証
helm lint --strict charts/<app>
helm lint --strict charts/<app> -f charts/<app>/values-production.yaml
helm template <app> charts/<app> -f charts/<app>/values-production.yaml \
| docker run --rm -i ghcr.io/yannh/kubeconform:v0.8.0 -strict -summary -kubernetes-version 1.34.0 -
出典
- https://helm.sh/docs/topics/charts/
- https://helm.sh/docs/chart_best_practices/
- https://helm.sh/docs/topics/registries/
- https://helm.sh/docs/overview/
- https://github.com/yannh/kubeconform
- https://kubernetes.io/docs/tasks/configure-pod-container/configure-liveness-readiness-startup-probes/
- https://kubernetes.io/docs/concepts/security/pod-security-standards/
- https://kubernetes.io/docs/concepts/scheduling-eviction/topology-spread-constraints/
- https://kubernetes.io/docs/concepts/workloads/pods/disruptions/
- https://argo-cd.readthedocs.io/en/stable/user-guide/helm/
- https://cert-manager.io/docs/usage/ingress/
- https://docs.github.com/en/packages/working-with-a-github-packages-registry/working-with-the-container-registry