こんにちは、moriです。
はじめに
先日、Mattermost v10が公開されましたが、MySQLによる新規構築がサポート外になるなどの変化があり、次のメジャーバージョンアップではMySQLが非推奨になる見込みです。
弊社でも、長らくMySQLでMattermostを運用してきましたが、これを機にPostgreSQLへの移行を検討することにしました。
なお、弊社では2つのMattermostインスタンスを運用しており、そのうち1つは投稿数が200万件を超える大規模なものです。
本記事では、移行にかかった時間や作業の流れについても解説していきます。
マイグレーションの流れ
以下の手順に沿って進めていきます。
- マイグレーションツール実行サーバの構築
- 新規Mattermostサーバの構築
- マイグレーションツールの実行
- 起動確認
- ELBの切り替え
基となる手順はMattermost公式の「Automated PostgreSQL migration」を参考にしました。
Step 1. マイグレーションツール実行サーバの構築
最初に、マイグレーションツールを動かすためのサーバを用意します。
弊社ではAWSのEC2インスタンスを利用し、以下のスペックで構築しました。
構築スペック
- スペック:s3.medium
- OS: AmazonLinux2023
- 事前にインストール:
git
、mysqlclient
、psql
(PostgreSQL Client)
使用するマイグレーションツールには、「migration-assist」と「pgloader」を使用します。
- migration-assist: MySQLからPostgreSQLへデータをスムーズに移行するための専用ツール
- pgloader: MySQLのデータを高速でPostgreSQLに移行するオープンソースツール
「migration-assist」のセットアップ
まず、GitHubから「migration-assist」をダウンロードします。
$ sudo mkdir /opt/migration-assist
$ cd /opt/migration-assist
$ sudo wget https://github.com/mattermost/migration-assist/releases/download/v0.3/migration-assist-Linux-x86_64.tar.gz
$ sudo tar -zxvf migration-assist-Linux-x86_64.tar.gz
「pgloader」のセットアップ
pgloaderのインストールにはsbcl(Steel Bank Common Lisp)が必要となります。以下がその手順です。
- sbclのバイナリファイルをダウンロードし、スクリプトでインストールします。
$ wget https://sourceforge.net/projects/sbcl/files/sbcl/2.3.6/sbcl-2.3.6-x86-64-linux-binary.tar.bz2
$ tar -xvf sbcl-2.3.6-x86-64-linux-binary.tar.bz2 cd sbcl-2.3.6-x86-64-linux
$ sudo ./install.sh
$ sbcl --version
- pgloaderのビルドに必要なツールをインストールします。
$ sudo yum install -y make gcc clang
$ sudo tee /etc/yum.repos.d/epel.repo <<EOL[epel]
name=Extra Packages for Enterprise Linux 9 - \$basearch
baseurl=https://download.fedoraproject.org/pub/epel/9/Everything/\$basearch/
enabled=1
gpgcheck=0
EOL
$ sudo yum clean all
$ sudo yum install -y freetds freetds-devel
- ソースコードからpgloaderをビルドし、インストールします。
$ git clone https://github.com/dimitri/pgloader.git
$ cd pgloader
$ make pgloader
$ sudo cp build/bin/pgloader /usr/local/bin/
$ sudo chmod +x /usr/local/bin/pgloader
インストール後、pgloader
コマンドが動作するか確認します。
$ pgloader --version
pgloader version "3.6.70f3557"
compiled with SBCL 2.3.6
Step 2. 新規Mattermostサーバの構築
移行先のMattermostを構築します(詳細なEC2やPostgreSQLの設定手順については割愛します)。
マイグレーションツール実行サーバから接続できるよう、pg_hba.conf
に設定を追加します。
下記を設定後にPostreSQLを再起動し、マイグレーションサーバからPostgresに接続できることを事前に確認してください。
例: マイグレーションツール実行サーバのIPが172.1.2.34/32
の場合
/var/lib/pgsql/data/pg_hba.conf
:
host all all 172.1.2.34/32 md5 #追加
:
Step 3. マイグレーションツールの実行
※接続情報は適宜読み替えてください。
"<MYSQL_DSN>"
は移行元のMYSQLへの接続情報になります。例 'xxuser:password@tcp(address:3306)/mattermost'
"<POSTGRES_DSN>"
は移行先のPosrgresSQLへの接続情報となります。例 'postgres://xxuser:password@address:5432/mattermost?sslmode=disable'
- 移行元のMySQLデータベースのスキーマ確認
$ /opt/migration-assist/migration-assist mysql "<MYSQL_DSN>"
サンプル出力:
$ /opt/migration-assist/migration-assist mysql 'xxuser:password@tcp(address:3306)/mattermost'
2024-11-05 23:26:16 pinging mysql...
2024-11-05 23:26:16 connected to mysql successfully...
2024-11-05 23:26:16 running checks for artifacts...
2024-11-05 23:26:16 a fix is required for: schema_migrations
2024-11-05 23:26:16 4 checks been made, 1 fix(es) is required for artifacts
2024-11-05 23:26:16 running checks for unicode...
2024-11-05 23:26:45 a fix is required for: linkmetadata_data
2024-11-05 23:27:20 a fix is required for: posts.props
2024-11-05 23:27:20 11 checks been made, 2 fix(es) is required for unicode
2024-11-05 23:27:20 running checks for varchar...
2024-11-05 23:27:20 8 checks been made, all good for varchar
2024-11-05 23:27:20 running checks for varchar-extended...
2024-11-05 23:27:44 a fix is required for: linkmetadata.url
2024-11-05 23:27:44 12 checks been made, 1 fix(es) is required for varchar-extended
必要に応じて--fix-artifacts --fix-unicode --fix-varchar
のオプションで修正を行ってください。
$ /opt/migration-assist/migration-assist mysql 'xxuser:password@tcp(address:3306)/mattermost' --fix-artifacts --fix-unicode --fix-varchar
すべてのチェックにクリアし場合は下記のような出力になります。※すべてall good
で結果が返されます。
$ /opt/migration-assist/migration-assist mysql 'xxuser:password@tcp(address:3306)/mattermost'
2024-11-03 23:10:02 pinging mysql...
2024-11-03 23:10:02 connected to mysql successfully...
Output file already exists, do you want to overwrite it? [y/N]: y
2024-11-03 23:10:09 running checks for artifacts...
2024-11-03 23:10:09 4 checks been made, all good for artifacts
2024-11-03 23:10:09 running checks for unicode...
2024-11-03 23:10:10 11 checks been made, all good for unicode
2024-11-03 23:10:10 running checks for varchar...
2024-11-03 23:10:10 8 checks been made, all good for varchar
2024-11-03 23:10:10 running checks for varchar-extended...
2024-11-03 23:10:10 12 checks been made, all good for varchar-extended
- 移行先のPostgreSQLデータベーススキーマ作成
$ /opt/migration-assist/migration-assist postgres "<POSTGRES_DSN>" --run-migrations --mattermost-version="<MATTERMOST_VERSION>"
# mattermost v9.11.0の場合の実行例となります
$ /opt/migration-assist/migration-assist postgres 'postgres://xxuser:password@address:5432/mattermost?sslmode=disable' --run-migrations --mattermost-version="9.11.0"
- pgloader設定の生成と実行
$ /opt/migration-assist/migration-assist pgloader --mysql="<MYSQL_DSN>" --postgres="<POSTGRES_DSN>" > migration.load
$ pgloader migration.load > migration.log
- 全文インデックスを復元する
$ /opt/migration-assist/migration-assist postgres post-migrate "<POSTGRES_DSN>"
- プラグイン関連のデータの移行する
$ /opt/migration-assist/migration-assist pgloader boards --mysql="<MYSQL_DSN>" --postgres="<POSTGRES_DSN>" > boards.load
$ /opt/migration-assist/migration-assist pgloader playbooks --mysql="<MYSQL_DSN>" --postgres="<POSTGRES_DSN>" > playbooks.load
$ /opt/migration-assist/migration-assist pgloader calls --mysql="<MYSQL_DSN>" --postgres="<POSTGRES_DSN>" > calls.load
$ pgloader boards.load > boards_migration.log
$ pgloader playbooks.load > playbooks_migration.log
$ pgloader calls.load > calls.log
- 新しい PostgreSQL データベースを利用するように Mattermost を構成する
今回は別サーバにMattermost と データベースを移行していきます。Mattermostとデータベースを分けている場合はMattermostの移行は不要でDSNの定義を変更ください。
# Mattermostを新サーバへ移行します
# 移行元サーバで実施します
$ sudo tar -czvf /tmp/mattermost_backup.tar.gz /opt/mattermost
$ scp /tmp/mattermost_backup.tar.gz user@<NEW_SERVER_IP>:/tmp
# 移行先サーバで実施します
$ sudo tar -xzvf /tmp/mattermost_backup.tar.gz -C /
$ sudo useradd --system --user-group mattermost
$ sudo chown -R mattermost:mattermost /opt/mattermost
$ sudo chmod -R g+w /opt/mattermost
Mattermostの起動ファイルを作成する
$ sudo touch /lib/systemd/system/mattermost.service
$ sudo vi /lib/systemd/system/mattermost.service # 以下の内容を記載します
[Unit]
Description=Mattermost
After=network.target
[Service]
Type=notify
ExecStart=/opt/mattermost/bin/mattermost
TimeoutStartSec=3600
KillMode=mixed
Restart=always
RestartSec=10
WorkingDirectory=/opt/mattermost
User=mattermost
Group=mattermost
LimitNOFILE=49152
[Install]
WantedBy=multi-user.target
systemctl をリロードします。
$ sudo systemctl daemon-reload
Mattermost のconfig.jsonファイルのDSNを書き換えます。
:
"DriverName": "postgres",
"DataSource": "postgres://xxuser:password@localhost/mattermost?sslmode=disable\u0026connect_timeout=10\u0026binary_parameters=yes",
:
Step 4. Mattermostの起動
Mattermostのconfig.json
にて接続設定を修正後、起動確認を行います。
$ systemctl start mattermost
$ systemctl status mattermost
必要な設定変更を終えたら、自動起動を有効にします。
$ systemctl enable mattermost
なお、起動時にMattermostがDBに接続できないエラーが発生することがありますが、公式ドキュメントにトラブルシューティングが記載されていますので、参考にしてください。
実際に弊社の移行時にも発生しました。どうやらsearch_path
の設定がおかしいことになっていました。以下のような手順で回避しています。
mattermost=> \dt
リレーションが見つかりませんでした。
mattermost=> SELECT usename, setting FROM pg_user u
JOIN pg_settings s ON u.usename = current_user
WHERE name = 'search_path';
usename | setting
----------+-----------------------------
xxuser | """""""$user"""", public"""
mattermost=> ALTER DATABASE mattermost SET search_path TO public, "$user";
mattermost=> ALTER USER xxuser SET search_path TO public, "$user";
mattermost=> SELECT usename, setting FROM pg_user u
JOIN pg_settings s ON u.usename = current_user
WHERE name = 'search_path';
usename | setting
----------+-----------------
xxuser | public, "$user"
ttermost=> \dt
リレーション一覧
スキーマ | 名前 | タイプ | 所有者
----------+----------------------------------+----------+----------
public | audits | テーブル | mmuseren
public | bots | テーブル | mmuseren
public | calls | テーブル | mmuseren
;
Step 5. ELBの切り替え
新しいMattermostをターゲットグループに追加し、旧Mysql環境のMattremostを除外します。(詳細な設定手順については割愛します)。
その他
200万件を実施した際の時間についても共有させていただきます。
なお、ステップ3で実施した、migration.logの最後にデータ移行にかかった時間がサマリ化されています。
table name errors rows bytes total time
------------------------------------ --------- --------- --------- --------------
before load 0 4 0.160s
fetch meta data 0 67 0.240s
Drop Foreign Keys 0 4 0.020s
------------------------------------ --------- --------- --------- --------------
mattermost.posts 0 2213848 962.8 MB 16m25.526s
mattermost.linkmetadata 0 1217760 678.0 MB 3m56.199s
mattermost.jobs 0 66736 8.9 MB 6.330s
mattermost.audits 0 54530 7.3 MB 5.830s
mattermost.threads 0 8320 1.1 MB 1.500s
mattermost.emoji 0 2551 231.5 kB 1.910s
mattermost.postspriority 0 779 46.4 kB 2.230s
mattermost.teammembers 0 288 19.8 kB 2.580s
mattermost.status 0 168 8.9 kB 3.240s
mattermost.incomingwebhooks 0 18 3.4 kB 3.620s
mattermost.commands 0 5 1.8 kB 3.940s
mattermost.oauthapps 0 2 0.6 kB 4.320s
mattermost.compliances 0 0 4.680s
mattermost.fileinfo 0 10614 34.2 MB 8.380s
mattermost.groupteams 0 0 5.010s
mattermost.persistentnotifications 0 0 5.320s
mattermost.retentionidsfordeletion 0 0 5.740s
mattermost.schemes 0 0 6.130s
mattermost.sharedchannels 0 0 6.500s
mattermost.usergroups 0 0 6.980s
mattermost.channelmembers 0 4077 940.9 kB 0.440s
mattermost.sidebarcategories 0 745 109.2 kB 0.670s
mattermost.sessions 0 289 69.3 kB 0.920s
mattermost.drafts 0 188 58.3 kB 1.300s
mattermost.roles 0 22 22.5 kB 1.590s
mattermost.useraccesstokens 0 10 1.0 kB 1.860s
mattermost.oauthaccessdata 0 2 0.4 kB 2.150s
mattermost.commandwebhooks 0 0 2.490s
mattermost.groupmembers 0 0 2.930s
mattermost.outgoingoauthconnections 0 0 3.250s
mattermost.remoteclusters 0 0 3.600s
mattermost.retentionpoliciesteams 0 0 4.080s
mattermost.sharedchannelusers 0 0 4.550s
mattermost.uploadsessions 0 0 4.400s
mattermost.threadmemberships 0 19920 1.6 MB 1.840s
mattermost.channelmemberhistory 0 4430 308.5 kB 0.650s
mattermost.channels 0 970 204.8 kB 1.440s
mattermost.productnoticeviewstate 0 470 28.3 kB 0.510s
mattermost.users 0 196 109.7 kB 1.410s
mattermost.systems 0 65 2.7 kB 1.250s
mattermost.teams 0 12 1.8 kB 1.520s
mattermost.outgoingwebhooks 0 3 1.0 kB 1.630s
mattermost.clusterdiscovery 0 0 1.610s
mattermost.groupchannels 0 0 1.600s
mattermost.notifyadmin 0 0 1.650s
mattermost.postreminders 0 0 1.750s
mattermost.retentionpolicieschannels 0 0 1.910s
mattermost.sharedchannelremotes 0 0 1.730s
mattermost.tokens 0 0 1.890s
mattermost.reactions 0 25765 3.0 MB 1.010s
mattermost.preferences 0 6980 608.7 kB 0.460s
mattermost.sidebarchannels 0 1538 167.8 kB 0.240s
mattermost.pluginkeyvaluestore 0 547 8.5 MB 1.010s
mattermost.publicchannels 0 244 29.6 kB 0.880s
mattermost.recentsearches 0 112 17.4 kB 0.430s
mattermost.bots 0 20 2.2 kB 0.850s
mattermost.oauthauthdata 0 3 0.6 kB 0.830s
mattermost.channelbookmarks 0 0 0.790s
mattermost.desktoptokens 0 0 0.790s
mattermost.licenses 0 0 0.730s
mattermost.postacknowledgements 0 0 0.950s
mattermost.retentionpolicies 0 0 1.000s
mattermost.sharedchannelattachments 0 0 0.940s
mattermost.termsofservice 0 0 0.920s
mattermost.usertermsofservice 0 0 0.920s
------------------------------------ --------- --------- --------- --------------
COPY Threads Completion 0 8 16m25.476s
Reset Sequences 0 0 0.350s
Create Foreign Keys 0 2 0.060s
Set Search Path 0 1 0.020s
Install Comments 0 0 0.000s
after load 0 4 0.190s
------------------------------------ --------- --------- --------- --------------
Total import time ✓ 3642227 1.7 GB 16m26.096s
メインの投稿データであるmattermost.posts
は17分弱かかっていることがわかります。
その他の手順などの実施時間やトラブルシュートも対応したりしながらでの実施でしたので、今回、弊社で実施した際は、トータルで2時間程サービス停止させてしまいました。
データ移行はMattermostの停止を伴いますので、移行計画をする際のご参考にしていただければと思います。