by Angus Mak on January 15, 2014 // Short URL

Debugging Drush commands with Xdebug and PHPStorm

Oftentimes, I run into issues with drush commands that needed more debugging power than dpm() provides. In search for a way to debug PHP scripts from the CLI, or drush commands more specifically, I stumbled upon PHPStorm’s Zero-configuration Debugging which turned out to be perfect for the job.

First, you will need Xdebug installed. http://xdebug.org/ has some excellent documentation on installing XDebug. For OSX users, I would recommend using homebrew with the formulae here https://github.com/josegonzalez/homebrew-php.

In the CLI, we will need to set the XDEBUG_CONFIG variable.

In bash,

export XDEBUG_CONFIG="idekey=PHPSTORM"

Once Xdebug is installed and the XDEBUG_CONFIG variable set up, start a new project in PHPStorm. Click on the Magic Button to "Start Listen PHP Debug Connections"

Start Listen PHP Debug Connections

In the CLI, we can then run any drush command inside the drupal docroot and a breakpoint should trigger on the first line of drush.php.

Breakpoint

Set up breakpoints and debug like you normally would. As long as PHPStorm is listening for a connection and the XDEBUG_CONFIG variable is set, any PHP script run on the CLI will trigger the debugger to break on the first line of the script. Once you are done with debugging, click the Magic Button again to "Stop Listen PHP Debug Connections".

Drush commands always trigger a break at the first line, unless drush is included in the project. When that gets a little old, uncheck "Force break at the first line when a script is outside the project" to stop the break at the first line.

Force break at the first line when a script is outside the project

I am in the debugger so much I ended up with the xdebug.idekey set up in my php.ini permanently.

xdebug.idekey="PHPSTORM";

That way the XDEBUG_CONFIG variable is not necessary anymore. In fact, this way any PHP activities including browsing a local site will pass through the debugging as long as PHPStorm is listening for a connection. 

Angus Mak

Senior Developer

Want Angus Mak to speak at your event? Contact us with the details and we’ll be in touch soon.

Comments

Add Your Comment

Pedro Perez

not working

Hi, I did all the settings, but debugging is not working. What i did wrong?

Reply

neighborhooddrupaler

Thanks for the info. An

Thanks for the info. An example of the kind of thing that this can sleuth out would be cool too.

Reply

Mark Muhleder

In vagrant?

This is great as far as it goes, but what about if you're running your dev site in a vagrant VM? Any clues on how to debug Drush in that case?

I ended up having to install the site I was working on locally, and this worked then, so thanks for the tip anyway.

Reply

makangus

Apologies about the year long

Apologies about the year long delay. For anyone still interested, path mapping is the answer to debugging drush inside a vagrant box for me. Edit the server settings and check 'Use path mappings', then add the folder where drush.php is located on the host machine under 'File/Directory' and do the same for the vagrant box under 'Absolute path on the server'.

Reply

Iain Potter

Hi Mark,

Hi Mark,

Don't forget to update your xdebug configuration on the guest (vagrant) VM to connect to the host operating system too.

e.g.

xdebug.remote_host=your_host_ip

Reply

Iain Potter

Generally, yes, but

Generally, yes, but unfortunately that won't work for Drush commands directly in a VM, since you want to connect back to your host OS running your IDE (the listener).

Reply

Iain Potter

@mark you probably need to

@mark you probably need to modify your xdebug config (in an .ini file somewhere, either php.ini or xdebug.ini I'd guess) to point back to your host O/S. The setting you'll need is "xdebug.remote_host". Just set it to the IP of your host O/S, although keep in mind this will need to be the address of the virtualbox adaptor.

Additionally, you can specify a specific phpstorm server by setting the environment variable

PHP_IDE_CONFIG="serverName='your_server_name'"

Additionally, if your drush command spawns further PHP process, don't forget to increase the "Max simultaneous connections" value (you can see it in Angus' settings screenshot above) otherwise your drush job may appear to hang.

Reply

margots

hangs on drush_invoke_process

Thank you for the great post. I am trying run xdebug with PHPSTorm while developing Drush commands. Everything seems to work, except it hangs whenever my custom drush command call drush_invoke_process. Have you have this problem? Any ideas how to troubleshoot/fix?thanks

Reply

Iain Potter

Hey, you may want to check

Hey, you may want to check that the PHP process can actually establish the connection to the debugger. This would give the appearance of a 'hang', when really it's a problem establishing a connection between the two.

You could use a tool such as netstat to look for connections in a 'syn_sent' status?

Reply

q0rban

Yeah, this is annoying

What command are you running where this happens? For debugging a command that has a confirm step, what I'll often do is turn off debugging, execute the command, and then turn debugging back on when it gets to the confirm step. I'd love to hear other solutions people have found to get around this!

Reply

moliveira

Max simultaneous connections

I ran into this issue when I was trying to debug an update hook using Drush. In PHPStorm, there is a setting called Max. simultaneous connections, which defaults to 1. Increase that limit and it won't get hung up and will stop on breakpoints past the point when Drush spawns a new process. That should carry you through any confirm steps, or in general any place where Drush spawns child processes (drush qrc comes to mind).

https://www.dropbox.com/s/5ccf09gf6965qn2/Preferences_2015-05-05_08-54-4...

Reply

Mark

Works Perfectly, but I'd Like to Turn XDebug Off for CRON

This process seems to work very nicely, thanks! However, I worry that XDebug is unnecessarily taxing performance of some drush scripts I run via CRON. During CRON nobody is 'listening' for any XDebug chatter, so is there a command-line means of disabling XDebug (so that I might insert a command into my CRON job) so that XDebug doesn't run at all during the CRON?

Thanks in advance.

Reply

Iain Potter

Hi Mark,

Hi Mark,

You probably should disable the xdebug module on a production box anyway. However, in order to answer your question, just make sure that the environment variables described in the article aren't set in the cron job environment.

Reply

Add Your Comment