Xdebug with SSH tunnel on Docker for Mac

2019-06-01 17:27发布

问题:

I was reading a lot of posts from the Docker community recently on how to debug PHP application in the PHPStorm with the Docker for Mac. All of them contains pieces of useful information, but haven’t seen working solution in one place.

回答1:

Here is what did work for me.

Inside Docker Container

Edit xdebug configuration

# automatically start debugger on every request
xdebug.remote_enable=1
xdebug.remote_autostart=1
xdebug.remote_port=9000
# send all debug requests to 127.0.0.1, remote_connect_back should be turned off
xdebug.remote_connect_back = 0
xdebug.remote_host=127.0.0.1

#log all xdebug requests to see is it working correctly
xdebug.remote_log=/var/log/remote.log

Verify that xdebug works

At this point try to run PHP application. Log should contain such entries for every request:

I: Connecting to configured address/port: 127.0.0.1:9000 I: Connected to client. :-)

If you see something like this in the log, remote_host or remote_connect_back are configured incorrectly.

I: Checking remote connect back address. I: Checking header 'HTTP_X_FORWARDED_FOR'. I: Checking header 'REMOTE_ADDR'. I: Remote address found, connecting to 172.18.0.1:9000. W: Creating socket for '172.18.0.1:9000', poll: Operation now in progress. E: Could not connect to client. :-(

I've seen situations when Xdebug worked in CLI but not from the browser, when this issue appeared in the log, remote_connect_back=0 fixed it.

sshd configuration

In order to allow ssh tunnelling to the container: edit /etc/ssh/sshd_conf and add:

GatewayPorts yes

Restart sshd if needed (ideally this should be part of the Dockerfile).

On Host Machine

Start reverse SSH tunnel

Run this command and keep it in separate Terminal tab open: ssh -p {container_22_port} -R 9000:localhost:1111 root@127.0.0.1

where {container_22_port} is the port on host machine mapped to the exdposed 22 port on docker container. 9000 is the port used by Xdebug inside container, 1111 port that will be used by host machine to listen to Xdebug connections.

Test with netcat

At this point you can verify that Xdebug actually passes information from inside docker container to the host machine. Start netcat to see what is sent to the 1111 port and run php application:

nc -l 1111

You should see something like this:

<?xml version="1.0" encoding="iso-8859-1"?>
<init xmlns="urn:debugger_protocol_v1" xmlns:xdebug="http://xdebug.org/dbgp/xdebug" fileuri="file:///var/www/magento2/index.php" language="PHP" xdebug:language_version="7.0.12" protocol_version="1.0" appid="1006" idekey="XDEBUG_ECLIPSE"><engine version="2.5.0rc1"><![CDATA[Xdebug]]></engine><author><![CDATA[Derick Rethans]]></author><url><![CDATA[http://xdebug.org]]></url><copyright><![CDATA[Copyright (c) 2002-2016 by Derick Rethans]]></copyright></init>

Configure PhpStorm

Opne File->DefaultSettings, and there in Languages&Frameworks->PHP->Debug change Xdebug->Debug port to 1111 (the one we used to open ssh tunnel). PhpStorm should start accepting connections from xdebug at this point.

Are there any concerns with this approach?



回答2:

I found out that you don't need a SSH tunnel to get it to work.

Xdebug need only to connect out to the running IDE debugger but there might be some default ports already used like the one for FPM (9000).

Inside the container

Set the xdebug options as this:

xdebug.remote_enable = 1
xdebug.remote_host = localhost
xdebug.remote_port = 10000
xdebug.remote_connect_back = 1

Note: if using the nginx-proxy container as reverse proxy set your remote_host as the one you defined in the VIRTUAL_HOST

Using PhpStorm

  • File -> Settings
    • Languages & Frameworks
      • PHP
        • Servers: add one and set the host as localhost: 80 with Xdebug with Path mapping selected ... map the folder INSIDE the Docker (/var/www/) to the one
        • Debug: set the Xdebug port to 10000 with the Can accept external connections checked