Entornos de desarrollo en VirtualBox con XDebug y VS Code

Enviado por Juan el Dom, 08/04/2018 - 23:34
Bug & VS Code

Cuando trabajo desarrollo web prefiero generalmente trabajar desde una máquina virtual con VirtualBox con un entorno Linux. La idea de esto es mantener separado el entorno de desarrollo de mi computadora personal, ya sea una PC o una Mac, por diversas razones:

  1. Evito instalar más programas directamente en mi equipo: me refiero a los servicios Apache, MySQL, Ruby para la compilación de Sass, Git, npm, etc.
  2. Personalmente me resulta más cómodo trabajar con los comandos de consola de un entorno Linux, sobre todo cuando estoy trabajando desde una computadora con Windows donde a pesar de que existen algunas herramientas de shell para emular una terminal Unix, siempre será mejor trabajar con un auténtico servidor Unix-friendly.
  3. Generalmente los servidores hacia donde se despliegan los proyectos en producción son servidores basados en Unix. De la mano con el punto anterior, el desarrollar desde un principio los proyectos en un entorno lo más parecido posible a lo que hay en producción hará más transparente el movimiento de los proyectos al mundo real.
  4. La parte divertida: si arruinas algo en la configuración de tu servidor, no puede ser tan grave porque el problema estará aislado sin afectar el sistema operativo de tu computadora.

No he encontrado el Santo Grial de los entornos de desarrollo pero últimamente he encontrado muy cómoda esta manera de trabajar cuando se trata de codificar proyectos PHP en Visual Studio Code para ser depurados con XDebug, por lo que comparto la receta para quien desee probar:

Primero: el servidor

Para arrancar asumiré que tienes instalada una máquina virtual con Ubuntu 16 y todo el LAMP stack instalado y funcionando en VirtualBox. Los comandos que se dictan a continuación deben ser ejecutados por el usuario root o en su defecto, anteponiendo el comando sudo. Lo primero será instalar la librería de XDebug para PHP, para lo cual ejecutamos lo siguiente desde la terminal:

apt-get install php-xdebug

Lo que sigue es configurar el módulo recién instalado. En este ejemplo yo lo hago con nano, pero claro que puedes utilizar vim o cualquier editor de tu preferencia. Ojo también en la versión de PHP que estés utilizando (en mi caso 7.2), lo cual puede cambiar la ubicación del archivo.

nano /etc/php/7.2/mods-available/xdebug.ini

Y debemos agregar las siguientes líneas para obtener los stack traces propios de XDebug:

zend_extension=xdebug.so
xdebug.show_error_trace = 1

Ahora hay que editar el archivo de configuración de PHP de Apache:

 nano /etc/php/7.2/apache2/php.ini

Dentro del cual se agregan las siguientes líneas, cuyo objetivo es permitir que otros equipos se conecten a tu máquina virtual al servicio de XDebug:

[XDebug]
xdebug.remote_enable = 1
xdebug.remote_autostart = 1
xdebug.remote_connect_back = 1

Y con eso estamos listos. Será necesario reiniciar tu servicio Apache para que los cambios surtan efecto. Para comprobar que todo está correctamente configurado puedes corroborarlo en una página con phpinfo:

PHP Info

Segundo: Visual Studio Code

Para la parte del cliente habrá que instalar las siguientes extensiones de VS Code:

La configuración de estas dos extensiones se realizará por proyecto, o más propiamente dicho, por área de trabajo de VS Code.

Para configurar ftp-sync solamente hay que presionar F1 y ejecutar el comando Ftp-sync: Init, con lo que se generará un archivo ftp-sync.json en el área de trabajo de VS Code y donde hay que configurar los accesos de SFTP a la máquina virtual, algo similar a lo siguiente:

{
    "remotePath": "/var/www/miproyecto/",
    "host": "fischer.test",
    "username": "bobby",
    "password": "mipassword",
    "port": 22,
    "secure": false,
    "protocol": "sftp",
    "uploadOnSave": true,
    "passive": false,
    "debug": false,
    "privateKeyPath": null,
    "passphrase": null,
    "ignore": [
        "\\.vscode",
        "\\.git",
        "\\.DS_Store"
    ],
    "generatedFiles": {
        "uploadOnSave": true,
        "extensionsToInclude": [],
        "path": ""
    }
}

En este ejemplo, fischer.test es el nombre del host que he dado de alta en mi equipo para conectar siempre a mi máquina virtual y /var/www/miproyecto es donde se ubica la raíz del proyecto web que estamos trabajando.

Inicialmente hay que sincronizar el proyecto de igual forma con F1 y Ftp-sync: Remote to local si los archivos del proyecto ya están en el servidor. La única parte incómoda de este método es que tendremos que sincronizar cada archivo después de modificado, o bien, sincronizar toda una carpeta luego de modificar varios de sus archivos. Pero vamos, apenas serán un par de clics.

Pasando ahora a la configuración de PHP Debug, debes ir a la pestaña de Depurar de la barra lateral y hacer clic en el botón de configuración con un engrane:

VS Code Debug Config

Esto abrirá un archivo launch.json donde se configuran las opciones de PHP Debug donde deberemos integrar una configuración llamada pathMappings para la depuración remota, quedando más o menos de la siguiente manera:

{
    "configurations": [
        {
            "name": "Listen for XDebug",
            "type": "php",
            "request": "launch",
            "port": 9000,
            "pathMappings": {
                "/var/www/miproyecto": "${workspaceRoot}",
            }
        },
}

La clave del pathMapping debe ser la ubicación raíz del proyecto en la máquina virtual, es decir, la misma que utilizamos como remotePath en la configuración de ftp-sync; el valor corresponde a la raíz del proyecto en nuestra computadora, por lo que ${workspaceRoot} es suficiente para este caso.

Guarda el archivo de configuración y estás listo: ahora podrás colocar puntos de interrupción e inspeccionar variables como los grandes. Para iniciar el proceso de depuración, ve a la pestaña de Depurar de VS Code y haz clic en el botón de Iniciar depuración con la opción Listen for XDebug seleccionada.

My debug is working!

Y ahora sólo me queda darte un abrazo y desearte: ¡Que tengas una feliz depuración, amiguito!