diff --git a/src/Handler.php b/src/Handler.php index 19c53f36eb1231baedca4f82f2c96ba1cd63520c..df5e59892a2fb2eae1bd9ed76a13cc073b9c2fad 100644 --- a/src/Handler.php +++ b/src/Handler.php @@ -105,12 +105,11 @@ class Handler { // Directory where this plugin is being installed. $pluginRoot = $installationManager->getInstallPath($this->getPackage('lakedrops/d8-project-scaffold-developer')); - // Create contrib/custom dirs for modules, profiles, themes and drush. + // Create contrib/custom dirs for modules, profiles and themes. foreach ([ $webRoot . '/modules', $webRoot . '/profiles', $webRoot . '/themes', - 'drush', ] as $dir) { foreach (['contrib', 'custom'] as $subdir) { $path = $dir . '/' . $subdir; @@ -129,6 +128,8 @@ class Handler { 'settings/default', 'files/default/files', 'files/default/private', + 'drush', + 'tests', ] as $dir) { $path = $projectRoot . '/' . $dir; if (!$fs->exists($path)) { @@ -181,6 +182,11 @@ class Handler { $fs->copy($pluginRoot . '/templates/drush/' . $template, 'drush/' . $template); } + // Copy Test files. + foreach (['phpunit.xml.dist'] as $template) { + $fs->copy($pluginRoot . '/templates/tests/' . $template, 'tests/' . $template); + } + // Link Drupal site's config directory. if (!$fs->exists($webRoot . '/sites/default/files/config')) { $rel = substr($fs->makePathRelative($projectRoot . '/config/default', $projectRoot . '/files/default/files/config'), 3, -1); diff --git a/src/TestSuite/Base.php b/src/TestSuite/Base.php new file mode 100644 index 0000000000000000000000000000000000000000..87f41e4cf75d289594a8c420a9b6d9beb8b1d16d --- /dev/null +++ b/src/TestSuite/Base.php @@ -0,0 +1,53 @@ +<?php + +namespace LakeDrops\Drupal8ScaffoldDeveloper\TestSuites; + +use Drupal\simpletest\TestDiscovery; +use PHPUnit\Framework\TestSuite; + +/** + * Base class for Drupal test suites. + */ +abstract class Base extends TestSuite { + + /** + * Finds extensions in a Drupal installation. + * + * An extension is defined as a directory with an *.info.yml file in it. + * + * @param string $root + * Path to the root of the Drupal installation. + * + * @return string[] + * Associative array of extension paths, with extension name as keys. + */ + protected function findExtensionDirectories($root) { + $paths = [ + $root . '/modules/custom', + $root . '/profiles/custom', + $root . '/themes/custom', + ]; + $extension_roots = array_filter($paths, 'file_exists'); + + $extension_directories = array_map('drupal_phpunit_find_extension_directories', $extension_roots); + return array_reduce($extension_directories, 'array_merge', []); + } + + /** + * Find and add tests to the suite for core and any extensions. + * + * @param string $root + * Path to the root of the Drupal installation. + * @param string $suite_namespace + * SubNamespace used to separate test suite. Examples: Unit, Functional. + */ + protected function addTestsBySuiteNamespace($root, $suite_namespace) { + foreach ($this->findExtensionDirectories($root) as $extension_name => $dir) { + $test_path = "$dir/tests/src/$suite_namespace"; + if (is_dir($test_path)) { + $this->addTestFiles(TestDiscovery::scanDirectory("Drupal\\Tests\\$extension_name\\$suite_namespace\\", $test_path)); + } + } + } + +} diff --git a/src/TestSuite/Functional.php b/src/TestSuite/Functional.php new file mode 100644 index 0000000000000000000000000000000000000000..2e901902b16305202d9d808708bdea8222d32ad6 --- /dev/null +++ b/src/TestSuite/Functional.php @@ -0,0 +1,27 @@ +<?php + +namespace LakeDrops\Drupal8ScaffoldDeveloper\TestSuites; + +require_once __DIR__ . '/Base.php'; + +/** + * Discovers tests for the functional test suite. + */ +class Functional extends Base { + + /** + * Factory method which loads up a suite with all functional tests. + * + * @return static + * The test suite. + */ + public static function suite() { + $root = dirname(dirname(dirname(dirname(dirname(__DIR__))))) . '/web'; + + $suite = new static('functional'); + $suite->addTestsBySuiteNamespace($root, 'Functional'); + + return $suite; + } + +} diff --git a/src/TestSuite/Unit.php b/src/TestSuite/Unit.php new file mode 100644 index 0000000000000000000000000000000000000000..c1dd80bb867ae3e708c7f9312bcc108f27b15457 --- /dev/null +++ b/src/TestSuite/Unit.php @@ -0,0 +1,27 @@ +<?php + +namespace LakeDrops\Drupal8ScaffoldDeveloper\TestSuites; + +require_once __DIR__ . '/Base.php'; + +/** + * Discovers tests for the unit test suite. + */ +class Unit extends Base { + + /** + * Factory method which loads up a suite with all unit tests. + * + * @return static + * The test suite. + */ + public static function suite() { + $root = dirname(dirname(dirname(dirname(dirname(__DIR__))))) . '/web'; + + $suite = new static('unit'); + $suite->addTestsBySuiteNamespace($root, 'Unit'); + + return $suite; + } + +} diff --git a/templates/tests/phpunit.xml.dist b/templates/tests/phpunit.xml.dist new file mode 100644 index 0000000000000000000000000000000000000000..4aff2ec2a5ef0a215873789ad3670958014a41dc --- /dev/null +++ b/templates/tests/phpunit.xml.dist @@ -0,0 +1,66 @@ +<?xml version="1.0" encoding="UTF-8"?> + +<!-- TODO set checkForUnintentionallyCoveredCode="true" once https://www.drupal.org/node/2626832 is resolved. --> +<!-- PHPUnit expects functional tests to be run with either a privileged user + or your current system user. See core/tests/README.md and + https://www.drupal.org/node/2116263 for details. +--> +<phpunit bootstrap="../web/core/tests/bootstrap.php" colors="true" + beStrictAboutTestsThatDoNotTestAnything="true" + beStrictAboutOutputDuringTests="true" + beStrictAboutChangesToGlobalState="true"> +<!-- TODO set printerClass="\Drupal\Tests\Listeners\HtmlOutputPrinter" once + https://youtrack.jetbrains.com/issue/WI-24808 is resolved. Drupal provides a + result printer that links to the html output results for functional tests. + Unfortunately, this breaks the output of PHPStorm's PHPUnit runner. However, if + using the command line you can add + - -printer="\Drupal\Tests\Listeners\HtmlOutputPrinter" to use it (note there + should be no spaces between the hyphens). +--> + <php> + <!-- Set error reporting to E_ALL. --> + <ini name="error_reporting" value="32767"/> + <!-- Do not limit the amount of memory tests take to run. --> + <ini name="memory_limit" value="-1"/> + <!-- Example SIMPLETEST_BASE_URL value: http://localhost --> + <env name="SIMPLETEST_BASE_URL" value=""/> + <!-- Example SIMPLETEST_DB value: mysql://username:password@localhost/databasename#table_prefix --> + <env name="SIMPLETEST_DB" value=""/> + <!-- Example BROWSERTEST_OUTPUT_DIRECTORY value: /path/to/webroot/sites/simpletest/browser_output --> + <env name="BROWSERTEST_OUTPUT_DIRECTORY" value=""/> + <!-- To disable deprecation testing completely uncomment the next line. --> + <!-- <env name="SYMFONY_DEPRECATIONS_HELPER" value="disabled"/> --> + <!-- Example for changing the driver class for mink tests MINK_DRIVER_CLASS value: 'Drupal\FunctionalJavascriptTests\DrupalSelenium2Driver' --> + <!-- Example for changing the driver args to mink tests MINK_DRIVER_ARGS value: '["http://127.0.0.1:8510"]' --> + <!-- Example for changing the driver args to phantomjs tests MINK_DRIVER_ARGS_PHANTOMJS value: '["http://127.0.0.1:8510"]' --> + <!-- Example for changing the driver args to webdriver tests MINK_DRIVER_ARGS_WEBDRIVER value: '["firefox", null, "http://localhost:4444/wd/hub"]' --> + </php> + <testsuites> + <testsuite name="unit"> + <file>../vendor/lakedrops/d8-project-scaffold-developer/src/TestSuite/Unit.php</file> + </testsuite> + <testsuite name="functional"> + <file>../vendor/lakedrops/d8-project-scaffold-developer/src/TestSuite/Functional.php</file> + </testsuite> + </testsuites> + <listeners> + <listener class="\Drupal\Tests\Listeners\DrupalListener"> + </listener> + <!-- The Symfony deprecation listener has to come after the Drupal listener --> + <listener class="Symfony\Bridge\PhpUnit\SymfonyTestsListener"> + </listener> + </listeners> + <!-- Filter for coverage reports. --> + <filter> + <whitelist> + <directory>../web/modules/custom</directory> + <directory>../web/profiles/custom</directory> + <directory>../web/themes/custom</directory> + <!-- By definition test classes have no tests. --> + <exclude> + <directory suffix="Test.php">./</directory> + <directory suffix="TestBase.php">./</directory> + </exclude> + </whitelist> + </filter> +</phpunit>