Vagrant上DockerコンテナのRailsをIDEでデバッグ

WindowsホストにVagrantゲストマシンがあり、Vagrantマシン上のDockerコンテナでRailsアプリが動いている状態。
開発に使っているWindows上のRubyMineでステップ実行したくなったので、環境を作りました。
docker-composeを使用しています。

※Rails・Docker共に初心者です。ツッコミ・補足等お待ちしています！

[最終的な設定・コマンド](#最終的な設定・コマンド)

# ruby-debug-ideをWindowsホストから利用する準備
## rdebug-ideを入れる

```Gruby:Gemfile
gem 'ruby-debug-ide'
gem 'debase'
```

## Vagrant <=> Dockerコンテナ間のポートフォワード設定
```ruby:docker-compose.yml
services:
  # ～略～
  rails:
    # ～略～
    ports:
      - 1234:1234    # 追加
      - 26162:26162  # 追加
```

## Windows <=> Vagrantのポートフォワード設定
以下をVagrantfileに追加。

```text:Vagrantfile
config.vm.network "forwarded_port", guest: 1234, host: 1234
```

## ruby-debugの実行
ここまでの設定反映のため、Windowsマシンで `vagrant reload` して、Vagrantマシンで `docker-compose up` する。
`docker-compose exec rails bash` でコンテナに入る。
ruby-debug-ideを実行する。

```
$ rdebug-ide --host 0.0.0.0 --port 1234 --dispatcher-port 26162 -- bin/rails s -b 0.0.0.0
```

「Fast Debugger ... listens on 0.0.0.0:1234」が表示され、IDEからの接続を待ち受ける状態になります。

# RubyMineから接続
Run => Edit Configurations で「＋」を押し、「Ruby remote dubug」を選択。
以下を設定

```
- Name: 好きな名前
- Remote host: 192.168.33.20    # Vagranfileで設定したVagrantのIPアドレス
- Remote port: 1234
- Remote root folder: /rails    # Dockerコンテナ内のrailsプロジェクトフォルダ
- Local port: 26162
- Local root folder: C:\vagrant\rails    #Windows内のrailsプロジェクト
```

`OK` でウィンドウを閉じたら、Run => Debug => ↑で設定した名前を選択。
（もしくは右上で設定を選択後、虫マークを押す）
Dockerコンテナのコンソールに戻ると、以下のようにメッセージが表示されます。

```
=> Booting Puma
=> Rails 5.1.5 application starting in development 
=> Run `rails server -h` for more startup options

Puma starting in single mode...
* Version 3.11.2 (ruby 2.5.1-p57), codename: Love Song
* Min threads: 5, max threads: 5
* Environment: development
* Listening on tcp://0.0.0.0:3000
```

これで接続成功！
・・・と、思いきや・・・

# ダメだった・・・

実行時の↑のメッセージに続いて、下のようなメッセージが表示され、ruby-debugが終了してしまいました。

```
Exiting
Uncaught exception: Address already in use - bind(2) for "0.0.0.0" port 3000
```

んー・・・`puma`で元から使っている3000番ポートと競合して怒られているような・・・？
rails初心者過ぎてそこらへんの挙動もよくわからない。

## HTTPポートを分けて対策
Docker起動時の`puma`実行を止めたり、プロセスkillしようとしたけどダメ。
ネットで事例を見ていると3000ポートのままでうまくいっているようなのですが、すっかり諦めて、ruby-debugのHTTP待ち受けでは別のポートを使うことにしました。
追加で、DockerとVagrantそれぞれのポートフォワーディングも必要（下記）。


# 最終的な設定・コマンド

```ruby:Gemfile
gem 'ruby-debug-ide'
gem 'debase'
```

```ruby:docker-compose.yml
services:
  # ～略～
  rails:
    # ～略～
    ports:
      - 1234:1234
      - 26162:26162
      - 4000:4000    # ruby-debugのHTTP接続用に使う
```

```text:Vagrantfile
config.vm.network "forwarded_port", guest: 1234, host: 1234
config.vm.network "forwarded_port", guest: 4000, host: 4000    # ruby-debugのHTTP接続用に使う
```

```bash:コマンドプロンプト（Windows）
$ vagrant reload
$ vagrant ssh
```

```bash:Vagrantゲスト
$ cd プロジェクトのディレクトリ
$ docker-compose up
$ docker-compose exec rails bash
```

```bash:dockerコンテナ
$ rdebug-ide --host 0.0.0.0 --port 1234 --dispatcher-port 26162 -- bin/rails s -b 0.0.0.0 -p 4000    #HTTP接続に4000番ポートを使う
```

```text:RubyMine
- Name: 好きな名前
- Remote host: 192.168.33.20    # Vagranfileで設定したVagrantのIPアドレス
- Remote port: 1234
- Remote root folder: /rails    # Dockerコンテナ内のrailsプロジェクトフォルダ
- Local port: 26162
- Local root folder: C:\vagrant\rails    #Windows内のrailsプロジェクト
```

# 結論
- やっぱりステップ実行は捗る
- 可及的速やかにMacを導入したい

# 参考
[【Windows7】VirtualBox ＋ Vagrant ＋ Ruby + Rails4 開発環境の構築【RubyMine編】](https://qiita.com/motomiya326/items/4648c389a12a3e00e270#ruby-debug-ide%E3%81%AE%E3%82%A4%E3%83%B3%E3%82%B9%E3%83%88%E3%83%BC%E3%83%AB)
[docker環境のrails5をstep実行でdebugする](https://qiita.com/pocari/items/9f83573272f2a2754a76)