vscodeでdockerに接続してxdebugでphpデバッグ

# 概要
VSCodeからdockerコンテナに接続してxdebugでphpデバッグする方法。
できてみたら簡単だったんだけど道を間違えて大はまりしたので残しておきます。

# 対象環境
VSCode on Windows
WSL2 + Docker Desktop、またはvagrant + docker

# 前提
- dockerコンテナでphpプログラムが動いてること
- phpにxdebugが入ってること

もしphpのコンテナにxdebugが入ってない場合は、Dockerfileに

```dockerfile
RUN pecl install xdebug && docker-php-ext-enable xdebug
```

とか付け足せばいけると思います。

# 予防線
VSCode初心者なので変な事してるかもしれません。

# 手順

## 1. php.iniの設定

### 概要
xdebugの設定をします。
vscodeでコンテナに接続してのデバッグなので、client_hostは127.0.0.1です。

### 手順
コンテナ内のphp.iniの `[xdebug]` セクションを、以下のようにします。

```ini:php.ini
[xdebug]

xdebug.client_host=127.0.0.1
xdebug.client_port=9003
xdebug.log=/tmp/xdebug.log
xdebug.log_level=7

xdebug.mode=debug
xdebug.start_with_request=yes
xdebug.start_upon_error=yes
xdebug.trigger_value=
```

この通りでないとだめなのは、 `client_host` , `client_port` , `mode` , `start_with_request` の4つです。
ほかは変えても大丈夫なはずです。

## 2. VSCodeを起動する

起動してください。

## 3. dockerを動かしている環境への接続（vagrantの場合のみ必要）

### 概要
vscodeを、dockerコンテナを検出できる状態にします。
具体的には、dockerの動いている環境に接続します。

### 不要な場合
WSL + Docker Desktop の場合は、VSCodeを起動した時点でコンテナを検出可能なので、ここは飛ばしてください。

### 手順

#### a. vagrantへ接続するためのssh設定
`c:\users\[username]\.ssh\config` に、vagrantにssh接続するための設定を書きます。

```ssh:.ssh/config
Host vagrant
    HostName 127.0.0.1
    Port 2222
    IdentityFile c:\users\kumanobori\.vagrant.d\insecure_private_key
    User vagrant
```

補足：ssh接続情報は、 `vagrant ssh-config` で見ることができます。

```ssh:ssh-config
c:\dev\vm\dev ssh-config
Host default
  HostName 127.0.0.1
  User vagrant
  Port 2222
  UserKnownHostsFile /dev/null
  StrictHostKeyChecking no
  PasswordAuthentication no
  IdentityFile C:/Users/kumanobori/.vagrant.d/insecure_private_key
  IdentitiesOnly yes
  LogLevel FATAL
````

補足：接続に失敗する場合はだいたい鍵絡みという印象でした。パスの書き方がおかしいとか、権限が自分以外にあるとか。VSCodeにログが出ているので丹念に調べましょう。。。

#### b. 拡張機能 Remote - SSH のインストール

拡張機能 `Remote - SSH` が入ってない場合は入れます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/35c74f34-73f1-b918-1b4d-a0f0f1949c34.png)

#### c. vagrantへの接続

1. コマンドパレットで `>remote-ssh: connect current window to host` を実行します。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/516bfaca-2640-f9ce-d96b-1ba02a0a50a1.png)
1. 少し待つと、前項で作成した `.ssh\config` の設定名が選択肢に出てくるので、それをクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/fff2bf11-1151-eccc-74a3-354f06100f55.png)
1. 少し待つと、接続先のOSを聞かれるので、Linuxをクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/a9679a51-5d38-2568-d700-a319e6cfe9d7.png)
1. 初回接続の場合はfingerprintの確認が出るので、continueをクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/8dca7291-455e-7739-395d-c663103d4639.png)
1. 接続が成功したら、VSCodeの画面の左下に接続先が表示されます。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/e11c9ba7-4647-8dec-e2a2-9f1c3831b37e.png)
1. エクスプローラの「フォルダーを開く」をクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/a084b434-a31a-4022-ba37-46878a4c486e.png)
1. Dockerfileまたはdocker-compose.ymlの格納されているディレクトリを入力し、開きます。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/a28d42f5-bd98-23f7-0565-504607154b3f.png) （補足：これをしておかないと、次工程の `Attach to Running Container` がうまくいきません）


## 4. コンテナへの接続

### 概要
vscodeを、コンテナに接続します。

### 手順

#### a. 拡張機能 Remote - Containers のインストール

拡張機能 `Remote - Containers` が入ってない場合は入れます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/7e30cb95-a971-d10b-3dc6-fd3cf2a68bbe.png)

#### b. コンテナへの接続

1. コマンドパレットで `Remote-Containers: Attach to Running Container` を実行します。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/cac9f274-774a-1f18-a44a-a4e8d1f521ed.png)
1. 少し待つと、稼働中コンテナが選択肢に出てくるので、phpコンテナをクリックします。
1. コンテナが新しいウィンドウで開きます。前のウィンドウは消しても問題ないです。
1. エクスプローラの「フォルダーを追加」をクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/a084b434-a31a-4022-ba37-46878a4c486e.png)
1. コンテナ内の、プロジェクトルートとなるべきディレクトリを指定します。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/10ca9a62-c863-ed2d-5593-a8853510bc65.png)
1. ファイルが表示されます。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/cbdc5059-3353-89af-8e58-96b45f1bc02f.png)

## 5. コンテナの設定

### 概要
コンテナ内でデバッグ実行のための設定をします。

#### a. コンテナの拡張機能設定

コンテナに拡張機能 `PHP Debug` が入っていない場合は入れます。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/c50cc7ba-21c7-9131-878c-dced7c5bcbf4.png)

#### b. コンテナのデバッグ設定

1. デバッグウィンドウの、「launch.jsonファイルを作成します」をクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/428a8724-a270-2e28-1b75-4ec2802b6f7e.png)
1. 言語を聞かれます。「PHP」にします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/3cc7fffe-d5ac-b965-5951-318c0fee2ef1.png) （補足：前工程でPHPデバッガを入れておかないと、ここでPHPが選択肢に出てきません。）
1. launch.json が生成されます。
1. jsonの `configurations` 内に `Listen for Xdebug`, `Launch currently open script`,  `Launch Build-in web server` の3つがあります。使うのは `Listen for Xdebug` だけなので、あとの2つは消します。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/e80dde04-d28a-a5a7-9442-1267ca66c736.png)
1. jsonにパスマッピング設定を追加します。${workspaceRoot} は、vscodeのエクスプローラーで開いているフォルダです。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/72858413-c9f4-af11-1cf9-ac145bf354dc.png)
1. Listen for Xdebug をクリックします。これでデバッグ開始です。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/282159/a541e445-441d-10bc-edb4-e79f9052a126.png)
1. どこか適当なところにブレークポイントを置いてみて、止まれば成功です。

# あとがき
vagrant経由のやり方は、ほかのリモートサーバに接続する場合にも使えそうです。
入れるデバッガとlaunch.jsonのところを変えれば、他の言語もいけそうな気がしてます。