クイックスタート:Dockerを使って5分でMaxScaleを試す
効果をすぐに確認するために、Docker Composeを使用します。この方法では、1台のMaster、1台 celestial Slave、そして1台のMaxScaleからなるテスト環境を素早く構築し、Read/Write Splitting(参照・更新分離)機能をテストできます。
以下の内容でdocker-compose.ymlファイルを作成します:
version: '3.8'
services:
mysql-master:
image: mariadb:10.6
environment:
MYSQL_ROOT_PASSWORD: root_password
MYSQL_DATABASE: testdb
ports:
- "3306:3306"
mysql-slave:
image: mariadb:10.6
environment:
MYSQL_ROOT_PASSWORD: root_password
depends_on:
- mysql-master
maxscale:
image: mariadb/maxscale:latest
volumes:
- ./maxscale.cnf:/etc/maxscale.cnf
ports:
- "6033:6033" # アプリケーション接続用ポート
- "8989:8989" # ダッシュボードGUI
depends_on:
- mysql-master
- mysql-slave
docker-compose up -dコマンドでシステムを起動します。これで、データベースの前面にインテリジェントなプロキシが配置されました。ポート6033に送信されるすべてのクエリは、MaxScaleによって適切なノードへ自動的にルーティングされます。
なぜProxySQLではなくMaxScaleを選ぶのか?
データベースクラスターの管理において、「アプリケーション側でどのIPがMaster(書き込み用)で、どのIPがSlave(読み取り用)かを意識したくない」という課題がよくあります。
MaxScaleはMariaDBチームによるその解決策です。ProxySQLと同じ目的を持ちますが、MaxScaleは.cnfファイルによる明快な設定が可能で、複雑なSQLiteインターフェースを介した操作が不要な点がメリットです。
実際に私が運用した50GBのデータを持つEコマースプロジェクトでは、Read/Writeを分離することでMasterの負荷を最大70%削減できました。重いレポート用のSELECTクエリを処理する代わりに、Masterはトランザクション処理のみに集中できるようになります。すべての読み取り負荷はSlaveに分散されます。
MySQLシステム向けMaxScaleの詳細設定
まず最初に、MySQL Masterでユーザーを作成します。このユーザーは、MaxScaleが各ノードのヘルスステータスを監視(モニタリング)するために使用されます。
-- MySQL Masterでこのコマンドを実行
CREATE USER 'maxuser'@'%' IDENTIFIED BY 'password123';
GRANT SELECT ON mysql.user TO 'maxuser'@'%';
GRANT SELECT ON mysql.db TO 'maxuser'@'%';
GRANT SELECT ON mysql.tables_priv TO 'maxuser'@'%';
GRANT SHOW DATABASES ON *.* TO 'maxuser'@'%';
GRANT REPLICATION CLIENT ON *.* TO 'maxuser'@'%';
FLUSH PRIVILEGES;
次に、ルーティングの「頭脳」を有効にするためにmaxscale.cnfファイルを構成します:
[maxscale]
threads=auto
# 1. データベースノードの定義
[server1]
type=server
address=mysql-master
port=3306
protocol=MariaDBBackend
[server2]
type=server
address=mysql-slave
port=3306
protocol=MariaDBBackend
# 2. モニター:2秒ごとにノードの状態を確認
[MariaDB-Monitor]
type=monitor
module=mariadbmon
servers=server1,server2
user=maxuser
password=password123
monitor_interval=2s
# 3. サービス:参照・更新(Read/Write)の自動分離
[Read-Write-Service]
type=service
router=readwritesplit
servers=server1,server2
user=maxuser
password=password123
# 4. リスナー:アプリからの受付ポート
[Read-Write-Listener]
type=listener
service=Read-Write-Service
protocol=MariaDBClient
port=6033
内部動作の仕組み:
- Monitor: ノードを継続的にチェックします。Masterに障害が発生した場合、MaxScaleはそれを検知し、データを保護するために書き込みフローを遮断します。
- Router (readwritesplit): SQL構文をリアルタイムで解析します。
INSERT/UPDATE/DELETEコマンドはMasterへ、SELECTは優先的にSlaveへ送信されます。 - Listener: 単一のエンドポイント(Endpoint)を提供します。アプリ側はポート6033を指す接続文字列(Connection String)を1つ用意するだけです。
同期遅延(Slave Lag)への根本的な対策
最も頭を悩ませるのは、MasterにデータをINSERTした直後にSlaveでSELECTしても, 同期遅延のためにデータが反映されていないという問題です。
MaxScaleは、[Read-Write-Service]内のパラメータでこの問題を非常にスマートに解決します:
[Read-Write-Service]
type=service
router=readwritesplit
max_slave_replication_lag=5
...
max_slave_replication_lag=5を設定すると、Slaveの遅延が5秒を超えた場合、MaxScaleは自動的に読み取りクエリをMasterへ送り返します。これにより、システムが同期負荷で遅延している時でも、ユーザーは常に最新のデータを確認できます。
運用における実戦的なアドバイス
プロキシを導入した多くのプロジェクトを経て、3つの重要な注意点をまとめました:
- ダッシュボードのセキュリティ: Webインターフェース(ポート 8989)のデフォルト設定は
admin/mariadbです。すぐにパスワードを変更するか、ファイアウォールでインターネットからのアクセスを遮断してください。 - Masterでのクエリ実行を強制する: ウォレットの残高確認など、精度の高いデータが必要な処理では、SQLヒント(
/* maxscale route to master */ SELECT ...)を使用して100%正確なデータを取得してください。 - デバッグログの活用: クエリが意図しない方向にルーティングされている場合は、
log_debug=1を有効にしてください。MaxScaleがなぜそのノードを選択したのか、ログファイルに詳細な理由が出力されます。
MaxScaleを導入することで、システムの負荷耐性が向上し、開発者は手動の接続管理から解放されます。設定過程で困ったことがあれば、お気軽に下のコメント欄で質問してください!

