トラブルシューティング¶
このページでは、Kubernetes クラスターのデプロイで CloudNativePG をトラブルシューティングする方法に関する基本的な情報を見つけることができます。
ヒント
Kubernetes 管理者として、 :ref:``kubectl` に cnpg プラグインを使用する<kubectl に cnpg プラグインを使用する>` ページをブックマークする必要があります。
始める前に¶
Kubernetes 環境¶
トラブルシューティング活動に違いをもたらすことができるのは、基盤となる Kubernetes システムに関する明確な情報を提供することです。
次のことを確認してください。
使用している Kubernetes のディストリビューションとバージョン
・PostgreSQLが稼働しているノードの仕様
実際の ストレージ容量の使用 についてできる限り、本番環境に入る前に行ったストレージ クラスとベンチマークを含みます。
クラスターで使用している関連する Kubernetes アプリケーション (つまり、Prometheus、Grafana、Istio、Certmanager など)
継続的なバックアップの状況、特に適切に機能しているかどうか: 正しく機能していない場合は、必ず 緊急バックアップ を実行してください。
潜在的な中断操作を実行する前に
便利なユーティリティ¶
必須の kubectl
ユーティリティに加えて、トラブルシューティングのために、システムで次のプラグイン/ユーティリティを使用できるようにすることをお勧めします。
kubectlの :ref:``kubectl` に cnpg プラグインを使用する<kubectl に cnpg プラグインを使用する>`jq 、軽量で柔軟なコマンドライン JSON プロセッサ
grep 、指定されたパターンに一致する行を含む 1
好みの *nix ディストリビューションをインストールし、上記のツールを使用します。
緊急バックアップ¶
緊急事態では、メインの app
データベースの緊急論理バックアップを作成する必要がある場合があります。
重要
以下の手順は、緊急時にのみ実行し、組織で有効なデータ保護ポリシーの下で一時バックアップ ファイルを保持する必要があります。ダンプ ファイルは実際に kubectl コマンドを実行するクライアント マシンに保存されるため、すべての保護が実施され、バックアップ ファイルを保存するのに十分なスペースがあることを確認してください。
次の例は、cluster-example-1 ポッドから、cluster-example
Postgres クラスター内の app
データベースの論理バックアップを取得する方法を示しています。
kubectl exec cluster-example-1 -c postgres \
-- pg_dump -Fc -d app > app.dump
注釈
環境で使用したオブジェクトの名前を指定することで、上記のコマンドをクラスターのバックアップに簡単に適用できます。
上記のコマンドは、カスタム形式で pg_dump
コマンドを発行します。これは、 logical backups in PostgreSQL
を取得する最も用途の広い方法です。
次のステップは、データベースを復元することです。初期化されたばかりの新しい
PostgreSQL クラスターで操作していると仮定します (つまり、app
データベースは空です)。
次の例は、プライマリ (new-cluster-example-1 ポッド)
に接続して、new-cluster-example Postgres クラスターの app
データベースで上記の論理バックアップを復元する方法を示しています。
kubectl exec -i new-cluster-example-1 -c postgres \
-- pg_restore --no-owner --role=app -d app --verbose < app.dump
重要
このセクションの例では、推奨に従って、ダンプおよび復元するグローバル オブジェクト (データベースとロール) が他にないことを前提としています。複数の役割がある場合は、pg_dumpall -g を使用してバックアップを作成し、それらを新しいクラスターに手動で復元していることを確認してください。複数のデータベースがある場合は、正しい所有権を割り当てていることを確認して、一度に 1 つのデータベースで上記の操作を繰り返す必要があります。 PostgreSQL に慣れていない場合は、これらの重要な操作を専門のサポート会社の指導の下で行うことをお勧めします。
上記の手順は、将来のある段階で cnpg
プラグインに統合される可能性があります。
ログ¶
CloudNativePG によって作成および制御されるすべてのリソースは、Kubernetes
によって期待されるように標準出力に記録され、JSON
format に直接記録されます。そのため、kubectl logs
コマンドを使用して特定のリソースからログを取得する必要があります。
詳細については、次のように入力してください。
kubectl logs --help
ヒント
JSON ログは機械読み取りには適していますが、人間には読み取りが困難です。使いやすさを向上させるために、jq コマンドを使用することをお勧めします。たとえば、kubectl logs コマンドを | jq -C で パイプ できます。
注釈
以下のセクションでは、CloudNativePG のトラブルシューティングに関して、さまざまなリソースに関するログを取得する方法の例をいくつか示します。
オペレーター情報¶
デフォルトでは、CloudNativePG オペレーターは Deployment として
Kubernetes の cnpg-system 名前空間にインストールされます
( 導入の詳細 を参照)。
詳細については)。
次のコマンドを実行して、オペレーター ポッドのリストを取得できます。
kubectl get pods -n cnpg-system
注釈
通常の状況では、cnpg-controller-manager- で始まる名前で識別される、オペレーターが実行されているポッドが 1 つ必要です。高可用性のためにオペレーターをセットアップした場合は、より多くのエントリーが必要です。これらのポッドは、cnpg-controller-manager という名前のデプロイメントによって管理されます。
以下を使用して、ポッド <POD>
で実行されているオペレーターに関する関連情報を収集します。
kubectl describe pod -n cnpg-system <POD>
次に、次のコマンドを実行して、同じポッドからログを取得します。
kubectl logs -n cnpg-system <POD>
オペレーターに関する詳細情報を収集する¶
以下を実行して、CloudNativePG オペレーター デプロイのすべてのポッドからログを取得します (マルチ オペレーター デプロイがある場合)。
kubectl logs -n cnpg-system \
deployment/cnpg-controller-manager --all-containers=true
Tip
上記のコマンドに -f フラグを追加して、リアルタイムでログを追跡できます。
次を実行して、ログを JSON ファイルに保存します。
kubectl logs -n cnpg-system \
deployment/cnpg-controller-manager --all-containers=true | \
jq -r . > cnpg_logs.json
kubectl-cnpg プラグインを使用して CloudNativePG
オペレーターのバージョンを取得します。
kubectl-cnpg status <CLUSTER>
出力:
Cluster in healthy state
Name: cluster-example
Namespace: default
System ID: 7044925089871458324
PostgreSQL Image: ghcr.io/cloudnative-pg/postgresql:15.2-3
Primary instance: cluster-example-1
Instances: 3
Ready instances: 3
Current Write LSN: 0/5000000 (Timeline: 1 - WAL File: 000000010000000000000004)
Continuous Backup status
Not configured
Streaming Replication status
Name Sent LSN Write LSN Flush LSN Replay LSN Write Lag Flush Lag Replay Lag State Sync State Sync Priority
- --- -------- --------- --------- ---------- --------- --------- ---------- ----- ---------- -------------
cluster-example-2 0/5000000 0/5000000 0/5000000 0/5000000 00:00:00 00:00:00 00:00:00 streaming async 0
cluster-example-3 0/5000000 0/5000000 0/5000000 0/5000000 00:00:00.10033 00:00:00.10033 00:00:00.10033 streaming async 0
Instances status
Name Database Size Current LSN Replication role Status QoS Manager Version
- --- ------------- ----------- ---------------- ------ --- ---------------
cluster-example-1 33 MB 0/5000000 Primary OK BestEffort 1.12.0
cluster-example-2 33 MB 0/5000000 Standby (async) OK BestEffort 1.12.0
cluster-example-3 33 MB 0/5000060 Standby (async) OK BestEffort 1.12.0
クラスタ情報¶
NAMESPACE 名前空間の <CLUSTER>
クラスターのステータスは、次のコマンドで確認できます。
kubectl get cluster -n <NAMESPACE> <CLUSTER>
出力:
NAME AGE INSTANCES READY STATUS PRIMARY
<CLUSTER> 10d4h3m 3 3 Cluster in healthy state <CLUSTER>-1
上記の例では、3 つのインスタンスからなる正常な PostgreSQL
クラスターが報告されています。これらはすべて ready
状態であり、<CLUSTER>-1 がプライマリです。
異常な状態の場合は、Cluster
リソースのマニフェストを取得することで、さらに多くのことを発見できます。
kubectl get cluster -o yaml -n <NAMESPACE> <CLUSTER>
収集するもう 1 つの重要なコマンドは、cnpg
プラグインによって提供される status コマンドです。
kubectl cnpg status -n <NAMESPACE> <CLUSTER>
Tip
--verbose オプションを追加すると、より多くの情報を出力できます。
注釈
クラスターの状態を知るだけでなく、cnpg プラグインを使用して次のことを行うこともできます。構成の変更を再ロードして適用するためのループ。<br /> 詳細については、 :ref:``kubectl` に cnpg プラグインを使用する<kubectl に cnpg プラグインを使用する>` のドキュメントを参照してください。
PostgreSQL コンテナー イメージのバージョンを取得します。
kubectl describe cluster <CLUSTER_NAME> -n <NAMESPACE> | grep "Image Name"
出力:
Image Name: ghcr.io/cloudnative-pg/postgresql:15.2-3
注釈
また、kubectl-cnpg status -n <NAMESPACE> <CLUSTER_NAME> を使用して同じ情報を取得できます。
ポッド情報¶
特定の PostgreSQL クラスターに属するインスタンスのリストを取得するには、次のコマンドを使用します。
kubectl get pod -l cnpg.io/cluster=<CLUSTER> -L role -n <NAMESPACE>
出力:
NAME READY STATUS RESTARTS AGE ROLE
<CLUSTER>-1 1/1 Running 0 10d4h5m primary
<CLUSTER>-2 1/1 Running 0 10d4h4m replica
<CLUSTER>-3 1/1 Running 0 10d4h4m replica
以下を実行することで、ポッドが失敗しているかどうか、またどのように失敗しているかを確認できます。
kubectl get pod -n <NAMESPACE> -o yaml <CLUSTER>-<N>
次のコマンドを使用して、特定の PostgreSQL インスタンスのすべてのログを取得できます。
kubectl logs -n <NAMESPACE> <CLUSTER>-<N>
検索を PostgreSQL プロセスのみに制限する場合は、次を実行できます。
kubectl logs -n <NAMESPACE> <CLUSTER>-<N> | \
jq select(.logger=="postgres") | .record.message
次の例では、ユーザー フレンドリな形式でタイムスタンプも追加します。
kubectl logs -n <NAMESPACE> <CLUSTER>-<N> | \
jq -r select(.logger=="postgres") | [(.ts|strflocaltime("%Y-%m-%dT%H:%M:%S %Z")), .record.message] | @csv
PostgreSQL ポッドに関する追加情報を収集してフィルタリングする¶
クラッシュした特定のポッドからのログを確認します。
kubectl logs -n <NAMESPACE> --previous <CLUSTER>-<N>
特定の PostgreSQL ポッドから FATAL エラーを取得します。
kubectl logs -n <NAMESPACE> <CLUSTER>-<N> | \
jq -r .record | select(.error_severity == "FATAL")
出力:
{
"log_time": "2021-11-08 14:07:44.520 UTC",
"user_name": "streaming_replica",
"process_id": "68",
"connection_from": "10.244.0.10:60616",
"session_id": "61892f30.44",
"session_line_num": "1",
"command_tag": "startup",
"session_start_time": "2021-11-08 14:07:44 UTC",
"virtual_transaction_id": "3/75",
"transaction_id": "0",
"error_severity": "FATAL",
"sql_state_code": "28000",
"message": "role \"streaming_replica\" does not exist",
"backend_type": "walsender"
}
特定のポッドのログで PostgreSQL DB エラー メッセージをフィルタリングします。
kubectl logs -n <NAMESPACE> <CLUSTER>-<N> | jq -r .err | select(. != null)
出力:
dial unix /controller/run/.s.PGSQL.5432: connect: no such file or directory
特定のポッドから err 単語に一致するメッセージを取得します。
kubectl logs -n <NAMESPACE> <CLUSTER>-<N> | jq -r .msg | grep "err"
出力:
2021-11-08 14:07:39.610 UTC [15] LOG: ending log output to stderr
特定のポッドの PostgreSQL プロセスからすべてのログを取得します。
kubectl logs -n <NAMESPACE> <CLUSTER>-<N> | \
jq -r . | select(.logger == "postgres") | select(.msg != "record") | .msg
``` 出力:
```shell
2021-11-08 14:07:52.591 UTC [16] LOG: redirecting log output to logging collector process
2021-11-08 14:07:52.591 UTC [16] HINT: Future log output will appear in directory "/controller/log".
2021-11-08 14:07:52.591 UTC [16] LOG: ending log output to stderr
2021-11-08 14:07:52.591 UTC [16] HINT: Future log output will go to log destination "csvlog".
値を含むフィールドでフィルター処理されたポッド ログを取得し、実行中の
| で区切られたそれらを結合します。
kubectl logs -n <NAMESPACE> <CLUSTER>-<N> | \
jq -r [.level, .ts, .logger, .msg] | join(" | ")
出力:
info | 1636380469.5728037 | wal-archive | Backup not configured, skip WAL archiving
info | 1636383566.0664876 | postgres | record
バックアップ情報¶
次のコマンドを使用して、名前付きクラスター用に作成されたバックアップを一覧表示できます。
kubectl get backup -l cnpg.io/cluster=<CLUSTER>
重要
バックアップのラベル付けは、CloudNativePG のバージョン 1.10.0 で導入されました。そのため、そのバージョンまたはそれ以降のバージョンで作成されたリソースのみに、そのようなラベルが含まれます。
保管情報¶
次のように、クラスターが使用する StorageClass を再確認して、調査またはトラブルシューティング中にさらにコンテキストを取得すると便利な場合があります。
STORAGECLASS=$(kubectl get pvc <POD> -o jsonpath={.spec.storageClassName})
kubectl get storageclasses $STORAGECLASS -o yaml
多くの場合、クラスターはデフォルトの StorageClass を使用して作成されるため、ここではクラスター ポッドの 1 つから StorageClass を取得しています。
ノード情報¶
Kubernetes ノードは、最終的に PostgreSQL ポッドが実行される場所です。それらについてできる限り多くのことを知ることは、戦略的に重要です。
以下を使用して、Kubernetes クラスター内のノードのリストを取得できます。
# look at the worker nodes and their status
kubectl get nodes -o wide
さらに、特定のクラスターのポッドが実行されているノードのリストを収集できます。
kubectl get pod -l cnpg.io/cluster=<CLUSTER> \
-L role -n <NAMESPACE> -o wide
- 後者は、ポッドが配布されている場所を理解するために重要です。
affinity/anti-affinity rules and/or tolerations を使用している場合は非常に便利です。
条件¶
多くのネイティブ kubernetes オブジェクト like here
と同様に、Cluster は status.conditions
も公開します。これにより、クラスター全体の正常性状態に頼るのではなく、特定のイベントが発生するのを「待つ」ことができます。現在利用可能な条件は次のとおりです。
LastBackupSucceeded
継続的なアーカイブ
準備
LastBackupSucceeded
は最新のバックアップのステータスを報告しています。 True
に設定されている場合、最後のバックアップが正しく取得され、それ以外の場合は
False に設定されます。
ContinuousArchiving は WAL アーカイブのステータスを報告しています。
True に設定されている場合、最後の WAL アーカイブ
プロセスが正常に終了し、それ以外の場合は False に設定されます。
クラスターにユーザーが指定した数のインスタンスがあり、プライマリ
インスタンスの準備が整っている場合、Ready は True
になります。この条件をスクリプトで使用して、クラスターが作成されるのを待つことができます。
特定の条件を待つ方法¶
バックアップ:
$ kubectl wait --for=condition=LastBackupSucceeded cluster/<CLUSTER-NAME> -n <NAMESPACE>
継続的なアーカイブ:
$ kubectl wait --for=condition=ContinuousArchiving cluster/<CLUSTER-NAME> -n <NAMESPACE>
準備完了 (クラスターの準備ができているかどうか):
edb_notranlate_39 以下は、失敗した状態を含む cluster.status
のスニペットです。
$ kubectl get cluster/<cluster-name> -o yaml
.
.
.
status:
conditions:
- message: unexpected failure invoking barman-cloud-wal-archive: exit status
2
reason: ContinuousArchivingFailing
status: "False"
type: ContinuousArchiving
- message: exit status 2
reason: LastBackupFailed
status: "False"
type: LastBackupSucceeded
- message: Cluster Is Not Ready
reason: ClusterIsNotReady
status: "False"
type: Ready
よくある問題¶
ストレージがいっぱいです¶
クラスター内の 1 つ以上のポッドが CrashloopBackoff
にあり、これがディスクがいっぱいであることが原因である可能性があることをログが示唆している場合、おそらくインスタンスの
PersistentVolumeClaim のサイズを増やす必要があります。ドキュメントの
ボリューム拡張 を見てください。
Pod が Pending 状態でスタックする¶
クラスターのインスタンスが Pending
フェーズでスタックしている場合は、ポッドの Events
セクションをチェックして、この背後にある理由を把握する必要があります。
kubectl describe pod -n <NAMESPACE> <POD>
これには、次のような原因が考えられます。
nodeSelectorに一致するノードがありません容認がノードのテイントに一致するように正しく構成されていない
ノードがまったく利用できない: これは、
cluster-autoscalerが制限に達したり、一時的な問題が発生したりすることにも関連している可能性があります
この場合、名前空間内のイベントを確認することも役立ちます。
kubectl get events -n <NAMESPACE>
# list events in chronological order
kubectl get events -n <NAMESPACE> --sort-by=.metadata.creationTimestamp
バックアップが構成されていない場合、レプリカは同期されません¶
メンテナンス上の理由により、レプリカがしばらくオフになることがあります (Kubernetes ノードがドレインされたときを考えてください)。クラスターにバックアップが構成されていない場合、レプリカが復旧したときに、プライマリにもう存在しない WAL ファイルが必要になる可能性があります ( :ref:``postgresql` セクション<postgresql セクション>` で説明されているように、WAL 管理ポリシーに従って既にリサイクルされています)。同期の。
同様に、pg_rewind が以前のプライマリに存在しなくなった WAL
ファイルを必要とする可能性がある場合、pg_rewind: error: could not open file
を報告します。
このような場合、Pod の準備ができなくなり、PVC を削除してオペレーターにレプリカの再構築を依頼する必要があります。
動的にプロビジョニングされた永続ボリュームに依存していて、PV 自体を削除する自信がある場合は、次の方法で削除できます。
PODNAME=<POD>
VOLNAME=$(kubectl get pv -o json | \
jq -r .items[]|select(.spec.claimRef.name==\"$PODNAME\")|.metadata.name)
kubectl delete pod/$PODNAME pvc/$PODNAME pvc/$PODNAME-wal pv/$VOLNAME