データベースのレプリケーション覚書

データベースのレプリケーション覚書です

いろいろ検索して調べてみて、やったが、今後忘れそうなので、メモしておくことにした。

マスター側の作業 と レプリケーションされる側(スレーブ側)の作業とに分かれてやることが多い。

最初にやっておくこととして、

レプリケーション用ユーザーの作成とレプリケーションサーバーの実行について

1.マスターサーバーでレプリケーション専用のユーザーを作成します。

CREATE USER ‘replication_user’@‘%’ IDENTIFIED BY ‘password’;
GRANT REPLICATION SLAVE ON *.* TO ‘replication_user’@‘%’;
FLUSH PRIVILEGES;

mysql > show master status;  を行い必要な情報を取得します。(ここだけ画像になります 等間隔のフォントで表示がうまくいかなかった。)

2.レプリカ側

mysql >
CHANGE MASTER TO
MASTER_HOST=’hostname’,
MASTER_USER=’replication_user‘,
MASTER_PASSWORD=’password’,
MASTER_LOG_FILE=’mysql-bin-changelog.263422′,
MASTER_LOG_POS=154;

実際に動かす時は、
START SLAVE;

 

 

 

方法が3つくらいある。

その1 データベースの容量が小さい場合

ステップ 1: マスターのデータをダンプ

    1. マスターサーバーでデータベースのダンプを作成します。
      レプリケーションの設定には、--master-dataオプションを使用して、バイナリログの位置情報も含めることが重要です。
      これにより、スレーブはこのバイナリログの位置からレプリケーションを開始できます。
mysqldump -u root -p --all-databases --master-data=2 > master_dump.sql

-pオプションの後にはパスワードを入力するか、プロンプトで入力します。
--all-databasesは全てのデータベースをダンプしますが、特定のデータベースのみをダンプしたい場合は、このオプションを適宜変更してください。

ステップ 2: ダンプファイルをスレーブに転送

    1. 作成したダンプファイルをスレーブサーバーに転送します。
      scprsyncなどのコマンドを使用できます。
scp master_dump.sql user@slave_server:/path/to/directory

ステップ 3: スレーブでダンプファイルをインポート

    1. スレーブサーバーで、転送したダンプファイルをMySQLデータベースにインポートします。
      mysql -u root -p < master_dump.sql

ステップ 4: レプリケーションの設定

    1. スレーブサーバーでレプリケーションを設定します。
      まず、MySQLにログインし、レプリケーション用のユーザーとその権限をマスターサーバーで作成していることを確認します。
      次に、スレーブサーバーで以下のコマンドを実行し、レプリケーションを開始します。

      CHANGE MASTER TO
      MASTER_HOST=’master_server_ip’,
      MASTER_USER=’replication_user’,
      MASTER_PASSWORD=’replication_password’,
      MASTER_LOG_FILE=’記録されたバイナリログファイル名’,
      MASTER_LOG_POS=記録されたバイナリログの位置;
      START SLAVE;

       

      MASTER_LOG_FILEMASTER_LOG_POSは、master_dump.sqlファイル内に記載されているバイナリログのファイル名と位置です。

ステップ 5: レプリケーションの状態を確認

    1. レプリケーションの状態を確認します。
      SHOW SLAVE STATUS\G

      Slave_IO_RunningSlave_SQL_Runningの両方がYesになっていれば、レプリケーションは正常に設定されています。

 プロセスを通じて、マスターサーバーのデータがスレーブサーバーにコピーされ、マスターからの更新がリアルタイムでスレーブに反映されるようになります。

 

その2 データベースの容量が大きい場合

ほとんどの場合がデータベースがデカくて、引っ越しが大変時間かかる、なんとかマスターから引っ張り出して、同期させるレプリケーションサーバーに入れ込みたい。
そこで、私は、テーブルごとにデータを移行するアプローチの方法を選択しました。
この方法では、データベース全体を一度に移行する代わりに、個々のテーブルを順番にダンプしてレプリケーションサーバーへと移行します。
このプロセスは、システムへの負荷を最小限に抑えると同時に、もし移行中に問題が発生した場合に影響範囲を限定しやすくなります。

 

テーブルごとのデータ移行手順

ステップ 1: テーブルの選定

    • 移行を開始する前に、どのテーブルを最初に移行するかを決定します。
      最も重要なデータ、またはサイズが小さく移行が比較的簡単なテーブルから始めるのが良いでしょう。

ステップ 2: テーブルのダンプ

    • mysqldumpツールを使用して、選択したテーブルのダンプを作成します。
      例えば、database_nameデータベースのtable_nameテーブルをダンプするには、以下のコマンドを使用します。

      mysqldump -u username -p database_name table_name > table_name.sql

ステップ 3: ダンプファイルの転送とインポート

    • ダンプファイルをレプリケーションサーバーに転送し、MySQLにインポートします。
      mysql -u username -p database_name < table_name.sql

注意点

    • 移行中のデータ整合性: データをテーブルごとに移行する場合、移行中にデータが更新される可能性があります。
      これを管理するためには、--single-transactionオプションを使用して一貫性のあるスナップショットを取得するか、移行中のテーブルを読み取り専用に設定することが重要です。
    • 移行作業の計画: 移行作業を実施する際は、データベースのダウンタイムやパフォーマンスへの影響を最小限に抑えるため、適切なタイミングを選択してください。

テーブルごとに移行するアプローチは、特に大規模なデータベースや、ダウンタイムを最小限に抑えたい場合に有効です。
計画的に進めることで、移行プロセスをスムーズに、かつ効率的に行うことが可能になります。

使い方

config.sh をつくる

mkdir replication
しておく。

table2table.shは、設定ファイルに機密情報(パスワードなど)を含める場合は、ファイルのアクセス権限を適切に設定して、不正アクセスを防ぐ必要があります。
chmod 600 config.sh
ファイルの所有者のみが読み書きできるように設定します。
table2table.shの権限を変更する
chmod +x ./table2table.sh

./table2table databese_name table_name

で実行する

 

例 config.sh

# config.sh

#master setting
USERNAME=’username’
PASSWORD=’master-password’
HOST=’master-host’

#replication setting
REPL_SERVER=’localhost’
REPL_PATH=’./replication’
REPL_DB_USERNAME=’replication-username’
REPL_DB_PASSWORD=’replication-password’

 

 

例 table2table.sh

# table2table.sh

#!/bin/bash

# 引数の確認
if [ “$#” -ne 2 ]; then
echo “Usage: $0 <db_name> <table_name>”
exit 1
fi

# コマンドライン引数からテーブル名を取得
DATABASE=$1
TABLE=$2

# 設定ファイルの読み込み
source ./config.sh

# 現在の日付をファイル名に使用
CURRENT_DATE=$(date +%Y%m%d_%H%M%S)

# 以下、スクリプトの内容…

# テーブルのダンプ
echo “Dumping table: $TABLE from database: $DATABASE”
mysqldump -u $USERNAME -h $HOST -p$PASSWORD $DATABASE $TABLE > “$REPL_PATH/${TABLE}_${CURRENT_DATE}.sql”
if [ $? -ne 0 ]; then
echo “Failed to dump table: $TABLE”
exit 1
else
echo “Dumped successfully: ${TABLE}_${CURRENT_DATE}.sql”
fi

# レプリケーションサーバーでのダンプファイルのインポート
echo “Importing dump file on replication server…”
echo “mysql -u $REPL_DB_USERNAME -p$REPL_DB_PASSWORD $DATABASE < $REPL_PATH/${TABLE}_${CURRENT_DATE}.sql”
mysql -u $REPL_DB_USERNAME -p$REPL_DB_PASSWORD $DATABASE < “$REPL_PATH/${TABLE}_${CURRENT_DATE}.sql”

 

if [ $? -ne 0 ]; then
echo “Failed to import dump file on replication server”
exit 1
else
echo “Import successful”
fi

echo “Process completed successfully”

Ubuntu mysql server  Fatal error: Illegal or unknown default time zone ‘Asia/Tokyo’ sudo systemctl restart mysql でエラーがでるとき。

Ubuntu mysql server  Fatal error: Illegal or unknown default time zone ‘Asia/Tokyo’  sudo systemctl restart mysql でエラーがでるとき。

その1

sudo systemctl status mysql.service

システムログの確認

Journalctlを使用してより詳細なエラーメッセージを確認します。

これにより、問題の原因を特定する手がかりが得られるかもしれません。

MySQLのログファイルを確認して、より詳細なエラーメッセージを探し、問題の原因を特定することが重要です。ログファイルは通常、/var/log/mysql/error.logにあります。

MySQLサーバーが起動に失敗している原因は、「Asia/Tokyo」というタイムゾーンが認識されない場合。

解決策

この問題を解決するためには、MySQLに’Tokyo’タイムゾーンを認識させる必要があります。以下の手順を実行してください。

ステップ1: タイムゾーン情報のインポート

MySQLのタイムゾーン情報は、システムのタイムゾーンデータベースからMySQLのデータベースにインポートする必要があります。
これを行うには、まずMySQLサーバーがタイムゾーン情報を格納するためのテーブルが存在するかどうかを確認し、必要に応じてこれらのテーブルを作成します。

mysql_tzinfo_to_sql /usr/share/zoneinfo | mysql -u root -p mysql

このコマンドは、システムのタイムゾーン情報(/usr/share/zoneinfo)を読み込み、それをMySQLにインポートします。
このコマンドを実行する際には、適切なMySQLのルートパスワードを入力する必要があります。

ステップ2: MySQLの設定変更

MySQLの設定ファイルを編集して、タイムゾーンを明示的に設定します。MySQLの設定ファイルは一般的に/etc/mysql/my.cnfやそのサブディレクトリにあります。このファイルを編集し、以下の行を[mysqld]セクションに追加または変更してください。

ini

[mysqld] default-time-zone = ‘Asia/Tokyo’

ステップ3: MySQLサーバーの再起動

sudo systemctl restart mysql

 

 

その2

これらの手順により、MySQLサーバーが’Tokyo’タイムゾーンを認識し、以前のエラーなしに起動するはずです。
もし依然として問題が発生する場合は、設定ファイルの変更が正しく行われているか、または他の設定が問題を引き起こしていないかを確認してください。

ステップ1: MySQLサービスの状態確認

まず、エラーの詳細を確認するためにMySQLサービスの状態を確認します。

sudo systemctl status mysql.service

ステップ2: システムログの確認

次に、journalctlを使用してより詳細なエラーメッセージを確認します。これにより、問題の原因を特定する手がかりが得られるかもしれません。

journalctl -xeu mysql.service

ステップ3: MySQL設定の確認

もし上記のログから具体的なエラー原因が明確でない場合、/etc/mysql/my.cnfファイルまたはその他の設定ファイルに追加したdefault-time-zoneの設定を一時的にコメントアウトしてみてください。

#[mysqld] #default-time-zone = ‘Asia/Tokyo’

その後、MySQLサービスを再起動してみてください。

sudo systemctl restart mysql

ステップ4: タイムゾーンの設定方法の再考

もしMySQLが’Asia/Tokyo’タイムゾーン設定で起動に失敗する場合、システム上でこのタイムゾーンが正しく認識されているか、またはタイムゾーン情報がMySQLに正しくインポートされているかを再確認してください。

MySQLがタイムゾーン情報を認識できるようにするためには、システムのタイムゾーンデータをMySQLのタイムゾーンテーブルにインポートする必要があります。この作業は以前のステップで実行しましたが、エラーメッセージやサーバーの状態を再確認して、このプロセスが正しく完了していることを確認してください。

ステップ5: MySQLのエラーログの確認

最後に、MySQLのエラーログを確認して、設定変更後に発生した具体的なエラーを確認します。

sudo cat /var/log/mysql/error.log

このログファイルには、MySQLサーバーの起動に失敗した具体的な原因が記録されている可能性があります。ログに記載されているエラーメッセージを基に、問題の解決策を探してください。

 

その3

 

もし問題が解決しない場合は、設定の変更を一つずつ元に戻してみるか、設定変更の影響を受ける可能性のある他の項目を確認してください。また、MySQLの公式ドキュメントやコミュニティフォーラムで類似の問題に関する情報を検索することも有効です。

default-time-zone = ‘Asia/Tokyo’ の設定が原因でMySQLが起動に失敗する場合、問題を解決するために別のアプローチを試みる必要があります。以下に、確認しながら進めるためのステップを示します。

ステップ1: タイムゾーンテーブルの確認

MySQLが Asia/Tokyo というタイムゾーンを認識できるようにする前に、MySQLのタイムゾーンテーブルに適切なデータが含まれていることを確認する必要があります。

  • MySQLサーバーにログインします。mysql -u root -p
  • タイムゾーンテーブルに Asia/Tokyo が含まれているかを確認します。SELECT * FROM mysql.time_zone_name WHERE Name = ‘Asia/Tokyo’;

    このクエリの結果が空であれば、タイムゾーン情報がデータベースにインポートされていないことを意味します。

ステップ2: タイムゾーン情報のインポート

タイムゾーンテーブルが空の場合、または Asia/Tokyo が見つからない場合は、システムのタイムゾーンデータをMySQLにインポートする必要があります。

sudo mysql_tzinfo_to_sql /usr/share/zoneinfo | sudo mysql -u root -p mysql

このコマンドはシステムのタイムゾーン情報をMySQLデータベースにインポートします。エラーが発生しないことを確認してください。

ステップ3: MySQLの設定変更

タイムゾーン情報が正しくインポートされたことを確認した後、MySQLの設定を直接変更する代わりに、サーバー起動時またはクライアント接続時にタイムゾーンを設定する方法を検討します。

  • サーバー起動時: MySQLサーバーを起動する際に、コマンドラインオプションでタイムゾーンを指定する方法があります。これは一般的にはサービスファイルや起動スクリプトを編集して行いますが、直接的な方法としては推奨されません。
  • クライアント接続時: アプリケーションやスクリプトからMySQLに接続する際に、セッションのタイムゾーンを設定することができます。例えば、PHPやPythonなどのプログラムから接続する際にタイムゾーンを指定することが可能です。

ステップ4: タイムゾーンの動的設定

アプリケーションがMySQLに接続した直後に、次のSQLコマンドを実行してセッションのタイムゾーンを設定することもできます。

sql

SET time_zone = ‘Asia/Tokyo’;

この方法を使用すれば、MySQLサーバー自体の設定を変更せずに、アプリケーションレベルでタイムゾーンを制御することが可能です。

注意点

  • タイムゾーン情報のインポート後にも default-time-zone = ‘Asia/Tokyo’ 設定でエラーが発生する場合は、MySQLサーバーのログファイルを再度確認して、エラーの詳細情報を見つけてください。
  • MySQLの設定やタイムゾーンの扱いに関しては、使用しているMySQLのバージョンによって挙動が異なる場合があるため、公式のドキュメントを参照することが重要です。