Bitnami Redmine(Windows)から自前Redmine(Windows)にデータ移行する手順

## まえがき
Windows Serverに自前で作ったRedmineにデータ移行するのは2度目ですが、はまりどころがいくつかあるため、備忘のため残しておきます。
※Ruby on Railsについて無知です。参考サイトを頼りに頑張りましたが、間違った点などあればご指摘ください。

## 前提
* 既存のBitnami版Redmineからデータ移行する(MySQL → MariaDB)  
※Bitnami版Redmineの最新バージョン(4.2.3-3)ではMariaDBが採用されており、自前構築に限界が来た場合にいつでも乗り換えられるようにMariaDBへ移行しておく。
* Apacheは使わず、IIS(ARR)を使う  
※IISのARRを使ってリバースプロキシでRedmineにつなげる。その場合、間にApacheを挟む意味があまりないと判断したため。

## 環境回り
| # | 移行元<br>[Redmine packaged by Bitnami](https://bitnami.com/stack/redmine/installer) (Version 4.1.0-0) | 移行先 |
|:-|:-|:-|
| OS | Windows Server 2012 R2 | Windows Server 2012 R2 |
| Redmine | 4.1.0.stable | 4.2.3.stable |
| Ruby | 2.5.7-p206 (2019-10-01) [x64-mingw32] | 2.6.9-p207 (2021-11-24) [x64-mingw32] |
| Rails | 5.2.4.1 | 5.2.6 |
| DB | MySQL(14.14 Distrib 5.7.28, for Win64 (x86_64)) | MariaDB(15.1 Distrib 10.4.22-MariaDB, for Win64 (AMD64))  |
| Appサーバー | thin/1.7.2 | thin/1.7.2 |
| Webサーバー | Apache/2.4.41  | IIS/10 |

## 手順
### 1. Ruby ([RubyInstaller for Window](https://rubyinstaller.org/))
  Redmineを動かすためにはRubyのインストールが必要。

1. ダウンロード
  公式サイトからインストーラーをダウンロードする
  [Ruby+Devkit 2.6.9-1 (x64)](https://github.com/oneclick/rubyinstaller2/releases/download/RubyInstaller-2.6.9-1/rubyinstaller-devkit-2.6.9-1-x64.exe)
  ※Redmineの[対応Rubyバージョン](https://redmine.jp/tech_note/supported-rubies/)によると2.7.2以降でも動くはずですが、途中で原因不明のエラーが起きて解決できなかったので、2.6.9を使う。
  
2. インストール
  手順に従ってインストールする。
  ※今回はインストール先をDドライブに変更：例）D:\Ruby26-x64
  ※後は全部デフォルトで(参考：[【Ruby on Rails】動作環境を構築するーーー2020.07 ver](https://www.chuken-engineer.com/entry/2020/08/18/102509))

### 2. MariaDB
  本番運用前提であればデータ保存先はsqliteよりもRDBMSにしておいた方がよい(らしい)。
  あと単純に現行がMySQLなのでデータ移行を簡略化するため。

1. ダウンロード
  公式サイトからインストーラーをダウンロードする。
  [MariaDB Server 10.4.22](https://mariadb.org/download/?t=mariadb&p=mariadb&r=10.4.22&os=windows&cpu=x86_64&pkg=msi&m=yamagata-university)
  Redmineの[インストールガイド(日本語版)](http://guide.redmine.jp/RedmineInstall/#Requirements)によるとMySQL5.7までとのことなので、MariaDB10.2 or 10.3ということになるはずですが、Bitnami版最新バージョンで10.4.22が使われていたので、合わせておく。
参考：[MariaDB と MySQL のバージョン比較](https://qiita.com/katzueno/items/e735950c7440f232ef27)

1. インストール
  手順に従ってインストールする。
  参考：[WindowsにMariaDBをインストールする手順](https://www.trifields.jp/how-to-install-mariadb-on-windows-2440)
  ※ポート番号が既存のMySQL等と被らないように注意すること！！
  ※既定でCドライブにDataフォルダが作られてしまう。
  　Dドライブに作りたい場合は、事前にCドライブにDataフォルダを作っておくと、インストーラが重複を検知して作成先を指定できるようになる。
  　例）C:\Program Files\MariaDB 10.4\data を作ってからインストーラを実行する。
  　※既定の場所はインストーラーのバージョンにより異なる。

### 3. Redmine
基本的に[公式の手順](http://guide.redmine.jp/RedmineInstall/#_3)に従ってインストールする
    
1. ダウンロード
  公式サイトからzipをダウンロードする。
  [redmine-4.2.3.zip](https://www.redmine.org/projects/redmine/wiki/Download)  
  
  1. 展開  
      zipを展開する(展開先は適宜)  
      例）D:\redmine-4.2.3
  1. 空のデータベースとユーザーの作成
      移行前のデータベース名とユーザー名に合わせておく。
      ※データベースは後でレストアするので作らなくても良いかもしれない。

        ```SQL
        CREATE DATABASE redmine CHARACTER SET utf8;
        CREATE USER 'redmine'@'localhost' IDENTIFIED BY '移行前とおなじパスワード';
        GRANT ALL PRIVILEGES ON redmine.* TO 'redmine'@'localhost';
        ```
        ※パスワードはRedmineの設定ファイルに記載されている。
        例）D:\Bitnami\redmine-4.1.0-0\apps\redmine\htdocs\config\database.yml

        ```ruby:database.yml
        production:
        adapter: mysql2
        database: bitnami_redmine
        host: 127.0.0.1
        username: bitnami
        password: **********
        # Use "utf8" instead of "utfmb4" for MySQL prior to 5.7.7
        encoding: utf8
        port: 3307
        ```
  1. データベースに接続するための設定
  `config/database.example.yml` をコピーして `config/database.yml` を作成する。
  そして `config/database.yml` を編集し、"production" 環境用のデータベース設定を行う。
  ※ `port` には新しくインストールしたデータベースのポート番号を指定すること！！
  例）

      ```ruby:config/database.yml
      production:
      adapter: mysql2
      database: bitnami_redmine
      host: 127.0.0.1
      username: bitnami
      password: **********
      # Use "utf8" instead of "utfmb4" for MySQL prior to 5.7.7
      encoding: utf8
      port: 3308
      ```
  1. メールサーバーに関する設定
      `config/configuration.example.yml` をコピーして `config/configuration.yml` を作成する。
      `config/configuration.yml` を編集し、"default:email_delivery:" の設定を行う。
      ※細かいメールサーバー設定は説明省略
      参考：https://guides.rubyonrails.org/action_mailer_basics.html#action-mailer-configuration  

  1. 依存するソフトウェアのインストール
      1. Bundlerをインストールする。※Rubyへのパスが通っている前提。
          
          ```cmd:cmd
          gem install bundler
          ```  
      1. 独自の依存関係の設定
          `thin` (Redmineを動かすためのアプリケーションサーバー) をインストールするため、Gemfile.localを作成する。
          ※Windowsサービス化するための `thin_service` も入れておく
          D:\redmine-4.2.3\Gemfile.local
          
          ```text:Gemfile.local
          gem "thin"
          gem "thin_service"
          ```
      1. Redmineを実行するために必要なソフトをインストールする。
          ※グローバルに入れると既存のRedmineに影響でそうなので、`--path vendor/bundle` をつける。
          　が、この書き方非推奨らしい警告が出るので、使えなくなったら新しい文法で対応が必要。
          
          ```cmd:cmd
          cd D:\redmine-4.2.3
          bundle install --without development test rmagick --path vendor/bundle
          ```
      1. セッションストア秘密鍵の生成
      
          ```cmd:cmd
          bundle exec rake generate_secret_token
          ```
          ※ここでエラーが発生して先に進めなくなりました。
          eventmachine云々というエラーで、[ここ](https://water2litter.net/rum/post/pc_redmine_windows/)を参考にしてリトライして成功。（根本原因は不明。。。）
          あと、再インストールしてもダメで、Gemfile.lockファイルを手で書き換えました。

          ```diff
          - eventmachine (1.2.7-x64-mingw32)
          + eventmachine (1.2.7)
          ```
      1. データベースバックアップ＆レストア
          既存のMySQLからデータをバックアップ

          ```cmd:cmd
          D:\Bitnami\redmine-4.1.0-0\mysql\bin>mysqldump -u bitnami -B bitnami_redmine -P 3307 -p > D:\Redmine-work\redmine-4.1.0-0_202201041028.dump
          ```
          新しく作ったMariaDBにレストア
          ※文字コードにUTF8を指定する
          `--default-character-set=utf8`

          ```cmd:cmd
          C:\Program Files\MySQL\MySQL Server 8.0\bin>mysql -u root -p -B bitnami_redmine -P 3308 --default-character-set=utf8 < "D:\Redmine-work\redmine-4.1.0-0_202201041334.dump"
          ```
      1. 添付ファイル、プラグインをバックアップ＆レストア  
          既存Redmineの `files`フォルダと `plugins`フォルダをそのまま新Redmineに移す。
          コマンド使ってもいいし、エクスプローラーでもいいし、よしなに。。。
      1. データベースのマイグレーション

          ```cmd:cmd
          set RAILS_ENV=production
          bundle exec rake db:migrate
          ```
      1. プラグインのマイグレーション

          ```cmd:cmd
          bundle exec rake redmine:plugins:migrate RAILS_ENV=production
          ```
      1. キャッシュクリア

          ```cmd:cmd
          bundle exec rake tmp:cache:clear RAILS_ENV=production
          ```
      1. Redmineにプレフィックスを付ける
          WebRoot直下ではなくて、`xxx.xxx.xxx/redmine` というURLで動かしたいので、Redmine側にプレフィックスを付ける。(ARRの設定等もこれに依存する)
          参考：[Application Request Routing(ARR)を使ったRedmineの設定について](https://blog.shibata.tech/entry/2017/11/05/214253)
      1. Windowsサービスに登録
          ※コマンドプロンプトを使っているせいか、文字コード関連でエラーになる。`RUBYOPT`を空にして対応。
          ※`--prefix "/redmine"` で起動時にプレフィックスをつけることができる。

          ```cmd:cmd
          set RUBYOPT=
          thin_service install -N "redmineThin-4.2.3" -c "D:\redmine-4.2.3" -p 3005 -e production --prefix "/redmine"
          ```

      1. リバースプロキシ設定
          IISのARRを使ってリバースプロキシを行う。

          ```
          DefaultWebSite
           └ redmine ← ここにアクセスして来たときにURL書き換えを行う。
          ```
          パターン： (.*)
          URLの書き換え：http://127.0.0.1:3005/redmine
          後続の規則処理を停止する： 停止する

          これで、`http[s]://xxx.xxx.xxx/redmine` にアクセスした場合に、thinで動かしているredmineに振り分けることができます。

## あとがき
  チケットに添付された日本語名ファイルをダウンロードすると、ファイル名の文字化けが発生。
  移行元のBitnami版でも同じ事象が発生していて、その際行ったのと同じ対処方法①を施してみたが、改善せず。
  対処方法①
  フォルダ    ：Redmine実行ディレクトリ\app\controllers
  ファイル名  ：application_controller.rb
  
```diff
- %r{(MSIE|Trident|Edge)}.match?(request.env['HTTP_USER_AGENT']) ? ERB::Util.url_encode(name) : name
+ %r{(MSIE|Trident|Edge|Chrome|Safari)}.match?(request.env['HTTP_USER_AGENT']) ? ERB::Util.url_encode(name) : name 
```

  別の対策で安定したので、これで様子見中。
  参考：[Rails日本語ファイル名がSafariやIEで文字化けする対策](https://qiita.com/rorensu2236/items/638d181e155b5dc5e35c)
  対処方法② 
  フォルダ    ：Redmine実行ディレクトリ\app\controllers
  ファイル名  ：application_controller.rb
  下記を末尾に追記
  
  ```ruby:application_controller.rb
  class ApplicationController < ActionController::Base
    def send_file_headers!(options)
      super(options)
      match = /(.+); filename="(.+)"/.match(headers['Content-Disposition'])
      encoded = URI.encode_www_form_component(match[2])
      headers['Content-Disposition'] = "#{match[1]}; filename*=UTF-8''#{encoded}" unless encoded == match[2]
    end
  end
  ```