Bei Mayflower ist es üblich, dass dem Entwicklerteam für jedes Projekt eine virtuelle Maschine zum Entwickeln zur Verfügung steht. Im einem unserer letzten Projekte hatten wir einen größeren Service auf Basis von Node.js zu erstellen. Dabei stellte sich heraus, dass das Debugging von JavaScript unter Node.js eine echte Herausforderung ist. Wie wir dennoch in unserem Setup mit der Entwickler-VM zum Debuggen gekommen sind, beschreibt dieser Artikel.
Disclaimer
Die folgende Anleitung sollte nur für Entwicklungs-VMs ohne öffentlichen Zugang gemacht werden.
Problemstellung
Der Debugger in der V8-Engine von Node.js horcht auf den Port 127.0.0.1:5858. Dadurch lassen sich Anfragen außerhalb der VM nicht direkt annehmen. Diese Einstellung ist in der V8-Engine hart codiert und kann nicht umgangen werden.
Lösung
Einrichten eines Proxies, der auf einen weiteren Port auf der VM hört und diesen dann auf 127.0.0.1:5858 weiterleitet. Das lässt sich mit Node.js sehr einfach und elegant umsetzen. Ein entsprechendes Port-Forwarding über SSH auf das Loopback-Interface der VM ist aber auch möglich. Ich werde nachfolgend die Lösung über das Skript beschreiben.
Wir haben das Skript gewählt, da wir unsere VMs mit Vagrant/Puppet verwalten und es sich dadurch sehr einfach automatisiert ausrollen lässt. Ein einfaches Port-Forwarding über die Vagrant-Konfiguration ist übrigens nicht möglich, da die immer nur auf das öffentliche Interface der Maschine leitet und nicht auf das gewünschte Loopback-Interface.
Konfiguration von PHPStorm
Anlegen einer neuen „Run/Debug Configuration“ und anschließend der Auswahl von Node.js Remote Debug. Konfiguration von Namen (frei wählbar), Host (IP oder Domain der VM) und Port 5859 (umstellen von Standard 5858)!

Einrichten des Proxy-Skripts
var net = require('net'), util = require('util'), portToCapture = 5859, portToPassThrough = 5858; net.createServer(function (capturingSocket) { var passThroughSocket = net.connect({ port: portToPassThrough }, function () { capturingSocket.pipe(passThroughSocket); passThroughSocket.pipe(capturingSocket); console.log('Connection to pass through socket established.'); }); }).listen(portToCapture); console.log(util.format('Created proxy listening on %s and redirecting to %s.', portToCapture, portToPassThrough));
GitHub: https://github.com/marco-jantke/misc/blob/master/NodeJS/debug_proxy.js
Das Skript muss nun noch auf der VM gestartet werden. Eine einfache Lösung ist es, das Skript als Upstart-Service einzurichten. Das kann dann über Puppet konfiguriert werden. Die Datei debug_proxy.js liegt bei uns im Projektverzeichnis unter /vagrant/files/debug_proxy.js. Wir haben für die Upstart-Skripte das Puppet-Modul https://github.com/bison/puppet-upstart verwendet.
# Import node.js debug_proxy script file { "/usr/local/bin/debug_proxy.js": source => '/vagrant/vagrant/files/debug_proxy.js', owner => 'vagrant', group => 'vagrant', } -> # Initialize the upstart module class {'::upstart': } -> ## Run the node_debug proxy upstart::job { 'node_debug_proxy': description => 'Starts the node debug proxy.', user => 'vagrant', group => 'vagrant', chdir => '/usr/local/bin', exec => 'node debug_proxy.js', }
Für alle die kein Puppet verwenden, hier nochmal das daraus generierte Upstart-Skript. Die Datei wird unter /etc/init/node_debug_proxy.conf angelegt.
# node_debug_proxy # # This upstart job configuration is managed by Puppet. # Do not edit this file. Your changes will be lost. description "Starts the node debug proxy." author "puppet-upstart" start on runlevel [2345] stop on runlevel [016] console log setuid vagrant setgid vagrant chdir /usr/local/bin exec node debug_proxy.js
Setzen der Haltepunkte
Das setzen der Haltepunkte wird Node.js über den Befehl debugger; signalisert. Zusätzlich muss aber auch in der gleichen Zeile in PHPStorm ein Haltepunkt gesetzt werden.
Achtung: Der Haltepunkt muss an einem Punkt gesetzt sein, an dem der Debugger durch eine vom User ausgelöste Aktion durchlaufen wird. Es direkt am Anfang einzurichten hat bei mir noch nicht geklappt, da man den Debugger in PHPStorm erst später startet.
Start der Applikation im Debug-Modus
Die Node-Applikation muss nun im –debug-Modus gestart werden. Dadurch wird dann auch der Listener auf Port 5858 geöffnet.
node --debug app.js
Start Debug-Session in PHPStorm
Nun einfach den Debugger in PHPStorm starten.
Auslösen einer Nutzerinteraktion
Anschließend geht man dann auf die Webseite/App und führt eine Aktion aus, die den Code an der Stelle des Haltepunkts durchlaufen lässt.
Viel Vergnügen! :-)
Lesenswert: node.js – Debugging in PHPStorm auf der VM http://t.co/PPWnxcCnFY
node.js – Debugging in PHPStorm auf der VM http://t.co/0vAoJ8XPQI via @mayflowerphp
node.js – Debugging in PHPStorm auf der VM http://t.co/xD0MFqxErv via @mayflowerphp
5858 > 5859 … debug mir ma Node in Storm … https://t.co/Ajrc09KNBP