5 min read

Writing and Executing PHPUnit Tests for a Single Shopware Plugin

A comprehensive guide on setting up, executing, and debugging PHPUnit tests specifically for a single Shopware plugin, ensuring execution from both the root and plugin directories.

Written by

PHPShopwareBackend Development

Writing and Executing PHPUnit Tests for a Single Shopware Plugin

This guide provides clear steps and detailed explanations on how to write, execute, and debug PHPUnit tests specifically for a single Shopware plugin, ensuring flexibility to run tests from the plugin directory or from the root of your Shopware project.

Prerequisites

  • Installed and configured Shopware 6 environment.
  • Composer installed.
  • PHPUnit as a development dependency (composer require --dev phpunit/phpunit).

Plugin Directory Structure

Your plugin should follow this recommended directory structure:

custom/plugins/MyCustomPlugin
├── src
│   └── ... (your plugin source files)
├── tests
│   └── ... (your PHPUnit test files)
├── composer.json
├── phpunit.xml.dist
└── tests/TestBootstrap.php

Step 1: Composer Autoload Configuration

Define autoload paths in your plugin's composer.json. This ensures PHPUnit can locate your test and source classes:

1{ 2 "autoload": { 3 "psr-4": { 4 "MyCustomPlugin\\": "src/" 5 } 6 }, 7 "autoload-dev": { 8 "psr-4": { 9 "MyCustomPlugin\\Tests\\": "tests/" 10 } 11 }, 12 "require-dev": { 13 "phpunit/phpunit": "^9.5", 14 "shopware/core": "*" 15 } 16}

Run composer dump-autoload in your plugin directory after making changes to ensure autoload settings are applied.

Step 2: PHPUnit Bootstrap Setup

Create tests/TestBootstrap.php in your plugin to ensure the correct test environment:

1<?php declare(strict_types=1); 2 3use Shopware\Core\TestBootstrapper; 4 5define('SHOPWARE_SKIP_DB_SETUP', 1); 6 7class MyCustomPluginTestBootstrapper extends TestBootstrapper 8{ 9 public function installPlugins(): self 10 { 11 // Skip plugin installation for faster unit tests 12 return $this; 13 } 14} 15 16$loader = (new MyCustomPluginTestBootstrapper()) 17 ->addCallingPlugin() 18 ->addActivePlugins('MyCustomPlugin') 19 ->setForceInstallPlugins(false) 20 ->bootstrap() 21 ->getClassLoader(); 22 23$loader->addPsr4('MyCustomPlugin\\Tests\\', __DIR__);

Important:

  • SHOPWARE_SKIP_DB_SETUP: Skips database setup to speed up tests. Only use this for pure unit tests. If database interactions or plugin installations are required, remove or comment this line.

Step 3: PHPUnit Configuration File

Create phpunit.xml.dist inside your plugin directory to define your test environment:

1<?xml version="1.0" encoding="UTF-8"?> 2<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 3 xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/9.3/phpunit.xsd" 4 bootstrap="tests/TestBootstrap.php" 5 executionOrder="random"> 6 <coverage> 7 <include> 8 <directory>./src/</directory> 9 </include> 10 </coverage> 11 <php> 12 <ini name="error_reporting" value="-1"/> 13 <server name="KERNEL_CLASS" value="Shopware\Core\Kernel"/> 14 <env name="APP_ENV" value="test"/> 15 <env name="APP_DEBUG" value="1"/> 16 <env name="SYMFONY_DEPRECATIONS_HELPER" value="weak"/> 17 </php> 18 <testsuites> 19 <testsuite name="MyCustomPlugin Testsuite"> 20 <directory>tests</directory> 21 </testsuite> 22 </testsuites> 23</phpunit>

Explanation:

  • Bootstrap: Points to your test bootstrap file.
  • Coverage: Specifies directories to include in code coverage.
  • Execution Order: Random execution order to detect inter-test dependencies.

Step 4: Global Autoload for Root Execution

If you want to run tests from the Shopware root, add a global autoload file (phpunit.autoload.php) at your Shopware root:

1<?php declare(strict_types=1); 2include_once __DIR__ . '/vendor/autoload.php'; 3 4$classLoader = new \Composer\Autoload\ClassLoader(); 5$pluginDirectories = glob(__DIR__ . '/custom/plugins/MyCustomPlugin*', GLOB_ONLYDIR); 6 7foreach ($pluginDirectories as $dir) { 8 foreach (['Tests', 'tests'] as $subdir) { 9 $testsDir = "$dir/$subdir"; 10 if (is_dir($testsDir)) { 11 $classLoader->addPsr4("MyCustomPlugin\\Tests\\", $testsDir, true); 12 } 13 } 14 15 $srcDir = "$dir/src"; 16 if (is_dir($srcDir)) { 17 $classLoader->addPsr4("MyCustomPlugin\\", $srcDir, true); 18 } 19} 20 21$classLoader->register();

Step 5: Running PHPUnit Tests

From Plugin Directory

Run tests from your plugin root directory:

1./vendor/bin/phpunit

From Shopware Root

Run your plugin-specific tests from the Shopware project root:

1./vendor/bin/phpunit --configuration="custom/plugins/MyCustomPlugin"

Run a specific testsuite or test method:

1./vendor/bin/phpunit --configuration="custom/plugins/MyCustomPlugin" --testsuite="MyCustomPlugin Testsuite" 2./vendor/bin/phpunit --configuration="custom/plugins/MyCustomPlugin" --filter testMethodName

Step 6: Debugging PHPUnit Tests

Tips for Debugging:

  • Use verbose output for detailed information:
1./vendor/bin/phpunit --verbose
  • Enable debugging in your test bootstrap by setting breakpoints or using var_dump and die() statements temporarily.

Important Considerations:

  • If tests fail due to missing Shopware components or services, ensure your plugin installation is not skipped by temporarily setting setForceInstallPlugins(true).
  • Check if your test environment closely matches your production environment to catch environment-specific issues early.

Common PHPUnit Commands

  • Run all tests:
1./vendor/bin/phpunit
  • Run a specific test suite:
1./vendor/bin/phpunit --testsuite="MyCustomPlugin Testsuite"
  • Run a specific test method:
1./vendor/bin/phpunit --filter="testMethodName"

Conclusion

Following these detailed steps ensures that you can easily write, execute, and debug your Shopware plugin tests effectively, maintaining flexibility and efficiency in your development and testing workflows.

About

Software Developer & Consultant specializing in JavaScript, TypeScript, and modern web technologies.

Share this article