MySQLを監視するための主要なメトリクス

By 清水 孝郎 - NOVEMBER 7, 2021

SHARE:

本文の内容は、2021年11月4日にDavid de Torres Huertaが投稿したブログ(https://sysdig.com/blog/mysql-monitoring/)を元に日本語に翻訳・再構成した内容となっております。

MySQL Prometheus エクスポーターを使えば、PrometheusでMySQLのモニタリングが簡単にできます。MySQLは紹介するまでもなく、世界で最も使用されているリレーショナル・データベースの一つであり、しかもオープンソースです。

このように人気のあるデータベースであるということは、それを支えるコミュニティも巨大であるということです。ですから、心配しないでください:あなたは一人ではありません。

illustration showing 5 cute little monitors with metrics in a podium
この記事では、Prometheus を使って MySQL サーバーの監視を行う方法を説明します。エクスポーターの設定から、主要なメトリクスは何か、アラートの例を交えて説明します。MySQL を RDS で運用している場合は、Amazon RDS を監視するためのトップ 5 キーメトリクスをお見逃しなく。

設定方法

エクスポーターをクラスターにデプロイする前に、データベースにエクスポーターのユーザーとパスワードを作成する必要があります。MySQLデータベースに入り、以下のクエリを実行します:
CREATE USER 'exporter'@'%' IDENTIFIED BY 'YOUR-PASSWORD' WITH MAX_USER_CONNECTIONS 3;
GRANT PROCESS, REPLICATION CLIENT, SELECT ON *.* TO 'exporter'@'%';

SQL文中のユーザー名とパスワードを、独自のものに置き換えてください。

エクスポーターのユーザー名とパスワードをデータベースに登録したら、エクスポーターの認証情報を記載したmysql-exporter.cnf ファイルを作成しなければなりません。また、このファイルには、MySQL データベースに接続するための URL を hostフィールドに記述します:

[client]
user = exporter
password = "YOUR-PASSWORD"
host=YOUR-DB-IP

Kubernetesクラスターでは、 mysql-exporter.cnfファイルでシークレットを作成します。このファイルは、データベースとの認証のためにエクスポーターにマウントされます。

kubectl create secret generic mysql-exporter \
  --from-file=.my.cnf=./mysql-exporter.cnf

MySQL Prometheus エクスポーターのデプロイ方法

Prometheus で MySQL の監視を開始するには、MySQL エクスポーター をクラスターにデプロイする必要があります。

エクスポーターをデプロイするには、以下のサンプルファイルを使用することができます。

---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: mysql-exporter-exporter
spec:
  selector:
    matchLabels:
      app: mysql-exporter
  replicas: 1
  template:
    metadata:
      labels:
        app: mysql-exporter
      annotations:
        prometheus.io/scrape: "true"
        prometheus.io/port: "9104"
    spec:
      containers:
        - name: mysql-exporter
          image: prom/mysqld-exporter:latest
          args:
            - --config.my-cnf=/tmp/.my.cnf
          ports:
            - containerPort: 9104
          volumeMounts:
            - name: my-cnf
              mountPath: /tmp/.my.cnf
              subPath: .my.cnf
          resources:
            limits:
              memory: "256Mi"
              cpu: "256m"
      volumes:
        - name: my-cnf
          secret:
            defaultMode: 420
            secretName: mysql-exporter
            items:
              - key: .my.cnf
                path: .my.cnf

エクスポーターのDeploymentを適用すると、Prometheusはすでに標準的なアノテーションを持っているので、自動的にMySQLのメトリクスのスクレイピングを開始します。

PrometheusでMySQLを監視するためのメトリクス Top 5

#1 可用性

MySQLインスタンスの可用性を監視するメトリクスは2つあります。1つ目はmysql_up。このメトリクスがゼロに等しい場合、エクスポーターはデータベースにアクセスできず、これはデータベースが不健康または故障しているという症状である可能性があります。

以下のクエリで、データベースがダウンした場合に通知するアラートを作成することができます:

mysql_up == 0

また、 mysql_global_status_uptimeというメトリクスは、前のメトリクスのレーダーの下を通過する可能性のある高速な再起動について知ることができます。以下のPrometheusクエリでアラートを作成し、アップタイムが30分未満のインスタンスを検出することができます。

mysql_global_status_uptime < 1800

#2 コネクション

データベースのエラーの主な原因のひとつは、接続エラーです。mysql_global_status_connection_errors_total というメトリクスを使うと、データベースがいつこれらのエラーを発生させているかを検出することができます:

rate(mysql_global_status_connection_errors_total[5m])

接続エラーの一般的な原因の 1 つは、利用可能な接続がないことです。このPrometheusのクエリーで、使用可能な接続の割合を確認することができます:

100 * mysql_global_status_threads_connected / mysql_global_variables_max_connections

この値が100に近い場合、データベースは新しい接続を拒否し始める可能性があります。この問題を解決するには、最大接続数を増やすことができます。その前に、システムで利用可能なオープンファイルの数を確認してください。以下のPrometheusのクエリーで確認できます。

mysql_global_variables_open_files_limit - mysql_global_variables_innodb_open_files

PromQLをもっと深く知りたいですか?PromQLの入門ガイドを読んで、Prometheusがどのようにデータを保存するか、PromQLの関数や演算子の使い方を学びましょう。


#3 スロークエリー

多くのデータベースと同様に、MySQLはスロークエリーのログを記録します。このログのエントリー数は、 mysql_global_status_slow_queriesというメトリクスで確認することができます。以下のPrometheusクエリーでアラートを作成すると、スロークエリーのログに新しいエントリがあったときに通知され、パフォーマンスの問題があることを意味します:

rate(mysql_global_status_slow_queries[5m])

#4 キャッシュヒット率

MySQLは、ディスクの読み書き操作を最適化するためにインメモリキャッシュを使用しています。キャッシュのヒット率が低いと、データベースのパフォーマンスに影響を与えます。このPrometheusのクエリーは、オープンテーブルのキャッシュヒット率の値を表示します。

rate(mysql_global_status_table_open_cache_hits[5m]) /
(rate(mysql_global_status_table_open_cache_hits[5m]) + rate(mysql_global_status_table_open_cache_misses[5m]))

また、以下のpromQLクエリでバッファプールキャッシュを監視することができます。

(rate(mysql_global_status_innodb_buffer_pool_read_requests[5m]) -
rate(mysql_global_status_innodb_buffer_pool_reads[5m])) / rate(mysql_global_status_innodb_buffer_pool_read_requests[5m]))

MySQLの設定でオープンテーブルやプールキャッシュのバッファサイズをチューニングすることができますが、そうするとインスタンスのメモリ使用量に影響することを覚えておいてください。十分なメモリがあることを確認してください。cAdvisor メトリクスを使用して、コンテナの利用可能なメモリを確認できます:

sum by (namespace,pod,container)((container_memory_usage_bytes{container!="POD",container!=""} -  on (namespace,pod,container) avg by (namespace,pod,container)(kube_pod_container_resource_limits{resource="memory"})) * -1 >0 ) / (1024*1024*1024)

MySQLインスタンスがAWS RDSにある場合は、RDSインスタンスの監視方法についてのブログ記事をご参照ください。

#5 クエリーの種類

MySQL データベースでは、SELECT クエリーの種類ごとに情報を提供するメトリクスを使用して、その使用状況の統計を取ることができます:

  • Full join: mysql_global_status_select_full_join
  • Full range join: mysql_global_status_select_full_range_join
  • Select range check (各行の後にキーの使用状況をチェックするキーなしで結合): mysql_global_status_select_range_check
  • Select scan: mysql_global_status_select_scan

いずれもカウンターなので、Prometheusのクエリーでは次のように関数rateを使うことを覚えておきましょう:

rate(mysql_global_status_select_full_join[5m])

同様に、MySQL でのソート クエリーの使用状況を統計を取ることもできます:

  • Sort rows: mysql_global_status_sort_rows
  • 範囲を使用して行われたソートの数: mysql_global_status_sort_range
  • Sort merge (ソートアルゴリズムが行わなければならなかったマージパスの数): mysql_global_status_sort_merge_passes
  • テーブルをスキャンして行われたソートの数: mysql_global_status_sort_scan

次のステップ

この記事では、Prometheus を使って MySQL のモニタリングを開始するのがいかに簡単かを学びました。必要なのは、適切なエクスポーターと設定だけです。
また、Prometheus で MySQL を監視する際に念頭に置くべき主要な Prometheus クエリーについても学びました。

Prometheus クエリーを書くためのインスピレーションを得たい場合は、Kubernetes を監視するための例を見たり、PromQL getting started cheatsheet をダウンロードしたりすることができます。

自分でPrometheusを管理したくないですか?

今すぐSysdig Monitorの無料トライアルに登録して、マネージド Prometheus サービスをご利用ください。Sysdig MonitorのPrometheusインテグレーションを試したり、Prometheus Remote Writeでメトリクスを送信することができます。

Sysdig Monitor screenshot showing the monitoring integrations setup page