Issue #2304461 by dawehner, neclimdul, naveenvalecha, jibran, tim.plunkett, phenaproxima, Xano, hussainweb, sun, hitesh-jain, amateescu, alexpott, daffie, Mile23, Wim Leers, larowlan: KernelTestBaseTNG™
parent
e76a96f48c
commit
d5821399fc
|
@ -210,7 +210,7 @@ function drupal_rewrite_settings($settings = array(), $settings_file = NULL) {
|
|||
}
|
||||
$variable_names['$'. $setting] = $setting;
|
||||
}
|
||||
$contents = file_get_contents(DRUPAL_ROOT . '/' . $settings_file);
|
||||
$contents = file_get_contents($settings_file);
|
||||
if ($contents !== FALSE) {
|
||||
// Initialize the contents for the settings.php file if it is empty.
|
||||
if (trim($contents) === '') {
|
||||
|
@ -315,7 +315,7 @@ function drupal_rewrite_settings($settings = array(), $settings_file = NULL) {
|
|||
}
|
||||
|
||||
// Write the new settings file.
|
||||
if (file_put_contents(DRUPAL_ROOT . '/' . $settings_file, $buffer) === FALSE) {
|
||||
if (file_put_contents($settings_file, $buffer) === FALSE) {
|
||||
throw new Exception(t('Failed to modify %settings. Verify the file permissions.', array('%settings' => $settings_file)));
|
||||
}
|
||||
else {
|
||||
|
|
|
@ -193,19 +193,23 @@ class FileStorage implements StorageInterface {
|
|||
* Implements Drupal\Core\Config\StorageInterface::listAll().
|
||||
*/
|
||||
public function listAll($prefix = '') {
|
||||
// glob() silently ignores the error of a non-existing search directory,
|
||||
// even with the GLOB_ERR flag.
|
||||
$dir = $this->getCollectionDirectory();
|
||||
if (!file_exists($dir)) {
|
||||
if (!is_dir($dir)) {
|
||||
return array();
|
||||
}
|
||||
$extension = '.' . static::getFileExtension();
|
||||
// \GlobIterator on Windows requires an absolute path.
|
||||
$files = new \GlobIterator(realpath($dir) . '/' . $prefix . '*' . $extension);
|
||||
|
||||
// glob() directly calls into libc glob(), which is not aware of PHP stream
|
||||
// wrappers. Same for \GlobIterator (which additionally requires an absolute
|
||||
// realpath() on Windows).
|
||||
// @see https://github.com/mikey179/vfsStream/issues/2
|
||||
$files = scandir($dir);
|
||||
|
||||
$names = array();
|
||||
foreach ($files as $file) {
|
||||
$names[] = $file->getBasename($extension);
|
||||
if ($file[0] !== '.' && fnmatch($prefix . '*' . $extension, $file)) {
|
||||
$names[] = basename($file, $extension);
|
||||
}
|
||||
}
|
||||
|
||||
return $names;
|
||||
|
@ -299,13 +303,15 @@ class FileStorage implements StorageInterface {
|
|||
$collections[] = $collection . '.' . $sub_collection;
|
||||
}
|
||||
}
|
||||
// Check that the collection is valid by searching if for configuration
|
||||
// Check that the collection is valid by searching it for configuration
|
||||
// objects. A directory without any configuration objects is not a valid
|
||||
// collection.
|
||||
// \GlobIterator on Windows requires an absolute path.
|
||||
$files = new \GlobIterator(realpath($directory . '/' . $collection) . '/*.' . $this->getFileExtension());
|
||||
if (count($files)) {
|
||||
$collections[] = $collection;
|
||||
// @see \Drupal\Core\Config\FileStorage::listAll()
|
||||
foreach (scandir($directory . '/' . $collection) as $file) {
|
||||
if ($file[0] !== '.' && fnmatch('*.' . $this->getFileExtension(), $file)) {
|
||||
$collections[] = $collection;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -195,10 +195,17 @@ class InstallStorage extends FileStorage {
|
|||
// We don't have to use ExtensionDiscovery here because our list of
|
||||
// extensions was already obtained through an ExtensionDiscovery scan.
|
||||
$directory = $this->getComponentFolder($extension_object);
|
||||
if (file_exists($directory)) {
|
||||
$files = new \GlobIterator(\Drupal::root() . '/' . $directory . '/*' . $extension);
|
||||
if (is_dir($directory)) {
|
||||
// glob() directly calls into libc glob(), which is not aware of PHP
|
||||
// stream wrappers. Same for \GlobIterator (which additionally requires
|
||||
// an absolute realpath() on Windows).
|
||||
// @see https://github.com/mikey179/vfsStream/issues/2
|
||||
$files = scandir($directory);
|
||||
|
||||
foreach ($files as $file) {
|
||||
$folders[$file->getBasename($extension)] = $directory;
|
||||
if ($file[0] !== '.' && fnmatch('*' . $extension, $file)) {
|
||||
$folders[basename($file, $extension)] = $directory;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -215,10 +222,17 @@ class InstallStorage extends FileStorage {
|
|||
$extension = '.' . $this->getFileExtension();
|
||||
$folders = array();
|
||||
$directory = $this->getCoreFolder();
|
||||
if (file_exists($directory)) {
|
||||
$files = new \GlobIterator(\Drupal::root() . '/' . $directory . '/*' . $extension);
|
||||
if (is_dir($directory)) {
|
||||
// glob() directly calls into libc glob(), which is not aware of PHP
|
||||
// stream wrappers. Same for \GlobIterator (which additionally requires an
|
||||
// absolute realpath() on Windows).
|
||||
// @see https://github.com/mikey179/vfsStream/issues/2
|
||||
$files = scandir($directory);
|
||||
|
||||
foreach ($files as $file) {
|
||||
$folders[$file->getBasename($extension)] = $directory;
|
||||
if ($file[0] !== '.' && fnmatch('*' . $extension, $file)) {
|
||||
$folders[basename($file, $extension)] = $directory;
|
||||
}
|
||||
}
|
||||
}
|
||||
return $folders;
|
||||
|
|
|
@ -15,6 +15,7 @@ use Drupal\Core\Config\BootstrapConfigStorageFactory;
|
|||
use Drupal\Core\Config\NullStorage;
|
||||
use Drupal\Core\Database\Database;
|
||||
use Drupal\Core\DependencyInjection\ContainerBuilder;
|
||||
use Drupal\Core\DependencyInjection\ServiceModifierInterface;
|
||||
use Drupal\Core\DependencyInjection\ServiceProviderInterface;
|
||||
use Drupal\Core\DependencyInjection\YamlFileLoader;
|
||||
use Drupal\Core\Extension\ExtensionDiscovery;
|
||||
|
@ -151,13 +152,16 @@ class DrupalKernel implements DrupalKernelInterface, TerminableInterface {
|
|||
protected $serviceYamls;
|
||||
|
||||
/**
|
||||
* List of discovered service provider class names.
|
||||
* List of discovered service provider class names or objects.
|
||||
*
|
||||
* This is a nested array whose top-level keys are 'app' and 'site', denoting
|
||||
* the origin of a service provider. Site-specific providers have to be
|
||||
* collected separately, because they need to be processed last, so as to be
|
||||
* able to override services from application service providers.
|
||||
*
|
||||
* Allowing objects is for example used to allow
|
||||
* \Drupal\KernelTests\KernelTestBase to register itself as service provider.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $serviceProviderClasses;
|
||||
|
@ -427,6 +431,21 @@ class DrupalKernel implements DrupalKernelInterface, TerminableInterface {
|
|||
return $this->container;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function setContainer(ContainerInterface $container = NULL) {
|
||||
if (isset($this->container)) {
|
||||
throw new \Exception('The container should not override an existing container.');
|
||||
}
|
||||
if ($this->booted) {
|
||||
throw new \Exception('The container cannot be set after a booted kernel.');
|
||||
}
|
||||
|
||||
$this->container = $container;
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
|
@ -514,7 +533,7 @@ class DrupalKernel implements DrupalKernelInterface, TerminableInterface {
|
|||
// Add site-specific service providers.
|
||||
if (!empty($GLOBALS['conf']['container_service_providers'])) {
|
||||
foreach ($GLOBALS['conf']['container_service_providers'] as $class) {
|
||||
if (class_exists($class)) {
|
||||
if ((is_string($class) && class_exists($class)) || (is_object($class) && ($class instanceof ServiceProviderInterface || $class instanceof ServiceModifierInterface))) {
|
||||
$this->serviceProviderClasses['site'][] = $class;
|
||||
}
|
||||
}
|
||||
|
@ -745,6 +764,13 @@ class DrupalKernel implements DrupalKernelInterface, TerminableInterface {
|
|||
}
|
||||
}
|
||||
|
||||
// If we haven't booted yet but there is a container, then we're asked to
|
||||
// boot the container injected via setContainer().
|
||||
// @see \Drupal\KernelTests\KernelTestBase::setUp()
|
||||
if (isset($this->container) && !$this->booted) {
|
||||
$container = $this->container;
|
||||
}
|
||||
|
||||
// If the module list hasn't already been set in updateModules and we are
|
||||
// not forcing a rebuild, then try and load the container from the disk.
|
||||
if (empty($this->moduleList) && !$this->containerNeedsRebuild) {
|
||||
|
@ -760,6 +786,7 @@ class DrupalKernel implements DrupalKernelInterface, TerminableInterface {
|
|||
}
|
||||
}
|
||||
|
||||
// If there is still no container, build a new one from scratch.
|
||||
if (!isset($container)) {
|
||||
$container = $this->compileContainer();
|
||||
}
|
||||
|
@ -1149,7 +1176,12 @@ class DrupalKernel implements DrupalKernelInterface, TerminableInterface {
|
|||
);
|
||||
foreach ($this->serviceProviderClasses as $origin => $classes) {
|
||||
foreach ($classes as $name => $class) {
|
||||
$this->serviceProviders[$origin][$name] = new $class;
|
||||
if (!is_object($class)) {
|
||||
$this->serviceProviders[$origin][$name] = new $class;
|
||||
}
|
||||
else {
|
||||
$this->serviceProviders[$origin][$name] = $class;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -7,6 +7,7 @@
|
|||
|
||||
namespace Drupal\Core;
|
||||
|
||||
use Symfony\Component\DependencyInjection\ContainerAwareInterface;
|
||||
use Symfony\Component\HttpKernel\HttpKernelInterface;
|
||||
use Symfony\Component\HttpFoundation\Request;
|
||||
|
||||
|
@ -16,7 +17,7 @@ use Symfony\Component\HttpFoundation\Request;
|
|||
* This interface extends Symfony's KernelInterface and adds methods for
|
||||
* responding to modules being enabled or disabled during its lifetime.
|
||||
*/
|
||||
interface DrupalKernelInterface extends HttpKernelInterface {
|
||||
interface DrupalKernelInterface extends HttpKernelInterface, ContainerAwareInterface {
|
||||
|
||||
/**
|
||||
* Boots the current kernel.
|
||||
|
|
|
@ -52,7 +52,7 @@ class PhpStorageFactory {
|
|||
$configuration['bin'] = $name;
|
||||
}
|
||||
if (!isset($configuration['directory'])) {
|
||||
$configuration['directory'] = DRUPAL_ROOT . '/' . PublicStream::basePath() . '/php';
|
||||
$configuration['directory'] = PublicStream::basePath() . '/php';
|
||||
}
|
||||
return new $class($configuration);
|
||||
}
|
||||
|
|
|
@ -127,6 +127,15 @@ abstract class LocalStream implements StreamWrapperInterface {
|
|||
$uri = $this->uri;
|
||||
}
|
||||
$path = $this->getDirectoryPath() . '/' . $this->getTarget($uri);
|
||||
|
||||
// In PHPUnit tests, the base path for local streams may be a virtual
|
||||
// filesystem stream wrapper URI, in which case this local stream acts like
|
||||
// a proxy. realpath() is not supported by vfsStream, because a virtual
|
||||
// file system does not have a real filepath.
|
||||
if (strpos($path, 'vfs://') === 0) {
|
||||
return $path;
|
||||
}
|
||||
|
||||
$realpath = realpath($path);
|
||||
if (!$realpath) {
|
||||
// This file does not yet exist.
|
||||
|
|
|
@ -331,10 +331,12 @@ class CKEditor extends EditorBase implements ContainerFactoryPluginInterface {
|
|||
if (empty($langcodes)) {
|
||||
$langcodes = array();
|
||||
// Collect languages included with CKEditor based on file listing.
|
||||
$ckeditor_languages = new \GlobIterator(\Drupal::root() . '/core/assets/vendor/ckeditor/lang/*.js');
|
||||
foreach ($ckeditor_languages as $language_file) {
|
||||
$langcode = $language_file->getBasename('.js');
|
||||
$langcodes[$langcode] = $langcode;
|
||||
$files = scandir('core/assets/vendor/ckeditor/lang');
|
||||
foreach ($files as $file) {
|
||||
if ($file[0] !== '.' && fnmatch('*.js', $file)) {
|
||||
$langcode = basename($file, '.js');
|
||||
$langcodes[$langcode] = $langcode;
|
||||
}
|
||||
}
|
||||
\Drupal::cache()->set('ckeditor.langcodes', $langcodes);
|
||||
}
|
||||
|
|
|
@ -33,6 +33,9 @@ use Symfony\Component\HttpFoundation\Request;
|
|||
* Additional modules needed in a test may be loaded and added to the fixed
|
||||
* module list.
|
||||
*
|
||||
* @deprecated in Drupal 8.0.x, will be removed before Drupal 8.2.x. Use
|
||||
* \Drupal\KernelTests\KernelTestBase instead.
|
||||
*
|
||||
* @see \Drupal\simpletest\KernelTestBase::$modules
|
||||
* @see \Drupal\simpletest\KernelTestBase::enableModules()
|
||||
*
|
||||
|
|
|
@ -0,0 +1,131 @@
|
|||
<?php
|
||||
|
||||
/**
|
||||
* @file
|
||||
* Contains \Drupal\simpletest\RandomGeneratorTrait.
|
||||
*/
|
||||
|
||||
namespace Drupal\simpletest;
|
||||
|
||||
use Drupal\Component\Utility\Random;
|
||||
|
||||
/**
|
||||
* Provides random generator utility methods.
|
||||
*/
|
||||
trait RandomGeneratorTrait {
|
||||
|
||||
/**
|
||||
* The random generator.
|
||||
*
|
||||
* @var \Drupal\Component\Utility\Random
|
||||
*/
|
||||
protected $randomGenerator;
|
||||
|
||||
/**
|
||||
* Generates a pseudo-random string of ASCII characters of codes 32 to 126.
|
||||
*
|
||||
* Do not use this method when special characters are not possible (e.g., in
|
||||
* machine or file names that have already been validated); instead, use
|
||||
* \Drupal\simpletest\TestBase::randomMachineName(). If $length is greater
|
||||
* than 3 the random string will include at least one ampersand ('&') and
|
||||
* at least one greater than ('>') character to ensure coverage for special
|
||||
* characters and avoid the introduction of random test failures.
|
||||
*
|
||||
* @param int $length
|
||||
* Length of random string to generate.
|
||||
*
|
||||
* @return string
|
||||
* Pseudo-randomly generated unique string including special characters.
|
||||
*
|
||||
* @see \Drupal\Component\Utility\Random::string()
|
||||
*/
|
||||
public function randomString($length = 8) {
|
||||
if ($length < 4) {
|
||||
return $this->getRandomGenerator()->string($length, TRUE, array($this, 'randomStringValidate'));
|
||||
}
|
||||
|
||||
// To prevent the introduction of random test failures, ensure that the
|
||||
// returned string contains a character that needs to be escaped in HTML by
|
||||
// injecting an ampersand into it.
|
||||
$replacement_pos = floor($length / 2);
|
||||
// Remove 2 from the length to account for the ampersand and greater than
|
||||
// characters.
|
||||
$string = $this->getRandomGenerator()->string($length - 2, TRUE, array($this, 'randomStringValidate'));
|
||||
return substr_replace($string, '>&', $replacement_pos, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Callback for random string validation.
|
||||
*
|
||||
* @see \Drupal\Component\Utility\Random::string()
|
||||
*
|
||||
* @param string $string
|
||||
* The random string to validate.
|
||||
*
|
||||
* @return bool
|
||||
* TRUE if the random string is valid, FALSE if not.
|
||||
*/
|
||||
public function randomStringValidate($string) {
|
||||
// Consecutive spaces causes issues for
|
||||
// \Drupal\simpletest\WebTestBase::assertLink().
|
||||
if (preg_match('/\s{2,}/', $string)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Starting or ending with a space means that length might not be what is
|
||||
// expected.
|
||||
if (preg_match('/^\s|\s$/', $string)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates a unique random string containing letters and numbers.
|
||||
*
|
||||
* Do not use this method when testing unvalidated user input. Instead, use
|
||||
* \Drupal\simpletest\TestBase::randomString().
|
||||
*
|
||||
* @param int $length
|
||||
* Length of random string to generate.
|
||||
*
|
||||
* @return string
|
||||
* Randomly generated unique string.
|
||||
*
|
||||
* @see \Drupal\Component\Utility\Random::name()
|
||||
*/
|
||||
protected function randomMachineName($length = 8) {
|
||||
return $this->getRandomGenerator()->name($length, TRUE);
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates a random PHP object.
|
||||
*
|
||||
* @param int $size
|
||||
* The number of random keys to add to the object.
|
||||
*
|
||||
* @return \stdClass
|
||||
* The generated object, with the specified number of random keys. Each key
|
||||
* has a random string value.
|
||||
*
|
||||
* @see \Drupal\Component\Utility\Random::object()
|
||||
*/
|
||||
public function randomObject($size = 4) {
|
||||
return $this->getRandomGenerator()->object($size);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the random generator for the utility methods.
|
||||
*
|
||||
* @return \Drupal\Component\Utility\Random
|
||||
* The random generator.
|
||||
*/
|
||||
protected function getRandomGenerator() {
|
||||
if (!is_object($this->randomGenerator)) {
|
||||
$this->randomGenerator = new Random();
|
||||
}
|
||||
return $this->randomGenerator;
|
||||
}
|
||||
|
||||
}
|
|
@ -28,6 +28,7 @@ use Drupal\Core\Utility\Error;
|
|||
abstract class TestBase {
|
||||
|
||||
use SessionTestTrait;
|
||||
use RandomGeneratorTrait;
|
||||
|
||||
/**
|
||||
* The test run ID.
|
||||
|
@ -283,13 +284,6 @@ abstract class TestBase {
|
|||
*/
|
||||
protected $configImporter;
|
||||
|
||||
/**
|
||||
* The random generator.
|
||||
*
|
||||
* @var \Drupal\Component\Utility\Random
|
||||
*/
|
||||
protected $randomGenerator;
|
||||
|
||||
/**
|
||||
* Set to TRUE to strict check all configuration saved.
|
||||
*
|
||||
|
@ -1417,113 +1411,6 @@ abstract class TestBase {
|
|||
new Settings($settings);
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates a pseudo-random string of ASCII characters of codes 32 to 126.
|
||||
*
|
||||
* Do not use this method when special characters are not possible (e.g., in
|
||||
* machine or file names that have already been validated); instead, use
|
||||
* \Drupal\simpletest\TestBase::randomMachineName(). If $length is greater
|
||||
* than 3 the random string will include at least one ampersand ('&') and
|
||||
* at least one greater than ('>') character to ensure coverage for special
|
||||
* characters and avoid the introduction of random test failures.
|
||||
*
|
||||
* @param int $length
|
||||
* Length of random string to generate.
|
||||
*
|
||||
* @return string
|
||||
* Pseudo-randomly generated unique string including special characters.
|
||||
*
|
||||
* @see \Drupal\Component\Utility\Random::string()
|
||||
*/
|
||||
public function randomString($length = 8) {
|
||||
if ($length < 4) {
|
||||
return $this->getRandomGenerator()->string($length, TRUE, array($this, 'randomStringValidate'));
|
||||
}
|
||||
|
||||
// To prevent the introduction of random test failures, ensure that the
|
||||
// returned string contains a character that needs to be escaped in HTML by
|
||||
// injecting an ampersand into it.
|
||||
$replacement_pos = floor($length / 2);
|
||||
// Remove 2 from the length to account for the ampersand and greater than
|
||||
// characters.
|
||||
$string = $this->getRandomGenerator()->string($length - 2, TRUE, array($this, 'randomStringValidate'));
|
||||
return substr_replace($string, '>&', $replacement_pos, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Callback for random string validation.
|
||||
*
|
||||
* @see \Drupal\Component\Utility\Random::string()
|
||||
*
|
||||
* @param string $string
|
||||
* The random string to validate.
|
||||
*
|
||||
* @return bool
|
||||
* TRUE if the random string is valid, FALSE if not.
|
||||
*/
|
||||
public function randomStringValidate($string) {
|
||||
// Consecutive spaces causes issues for
|
||||
// Drupal\simpletest\WebTestBase::assertLink().
|
||||
if (preg_match('/\s{2,}/', $string)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Starting or ending with a space means that length might not be what is
|
||||
// expected.
|
||||
if (preg_match('/^\s|\s$/', $string)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates a unique random string containing letters and numbers.
|
||||
*
|
||||
* Do not use this method when testing unvalidated user input. Instead, use
|
||||
* \Drupal\simpletest\TestBase::randomString().
|
||||
*
|
||||
* @param int $length
|
||||
* Length of random string to generate.
|
||||
*
|
||||
* @return string
|
||||
* Randomly generated unique string.
|
||||
*
|
||||
* @see \Drupal\Component\Utility\Random::name()
|
||||
*/
|
||||
public function randomMachineName($length = 8) {
|
||||
return $this->getRandomGenerator()->name($length, TRUE);
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates a random PHP object.
|
||||
*
|
||||
* @param int $size
|
||||
* The number of random keys to add to the object.
|
||||
*
|
||||
* @return \stdClass
|
||||
* The generated object, with the specified number of random keys. Each key
|
||||
* has a random string value.
|
||||
*
|
||||
* @see \Drupal\Component\Utility\Random::object()
|
||||
*/
|
||||
public function randomObject($size = 4) {
|
||||
return $this->getRandomGenerator()->object($size);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the random generator for the utility methods.
|
||||
*
|
||||
* @return \Drupal\Component\Utility\Random
|
||||
* The random generator
|
||||
*/
|
||||
protected function getRandomGenerator() {
|
||||
if (!is_object($this->randomGenerator)) {
|
||||
$this->randomGenerator = new Random();
|
||||
}
|
||||
return $this->randomGenerator;
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts a list of possible parameters into a stack of permutations.
|
||||
*
|
||||
|
|
|
@ -81,6 +81,7 @@ class TestDiscovery {
|
|||
|
||||
// Add PHPUnit test namespaces of Drupal core.
|
||||
$this->testNamespaces['Drupal\\Tests\\'] = [DRUPAL_ROOT . '/core/tests/Drupal/Tests'];
|
||||
$this->testNamespaces['Drupal\\KernelTests\\'] = [DRUPAL_ROOT . '/core/tests/Drupal/KernelTests'];
|
||||
$this->testNamespaces['Drupal\\FunctionalTests\\'] = [DRUPAL_ROOT . '/core/tests/Drupal/FunctionalTests'];
|
||||
|
||||
$this->availableExtensions = array();
|
||||
|
@ -98,6 +99,7 @@ class TestDiscovery {
|
|||
|
||||
// Add PHPUnit test namespaces.
|
||||
$this->testNamespaces["Drupal\\Tests\\$name\\Unit\\"][] = "$base_path/tests/src/Unit";
|
||||
$this->testNamespaces["Drupal\\Tests\\$name\\Kernel\\"][] = "$base_path/tests/src/Kernel";
|
||||
$this->testNamespaces["Drupal\\Tests\\$name\\Functional\\"][] = "$base_path/tests/src/Functional";
|
||||
}
|
||||
|
||||
|
|
|
@ -117,7 +117,7 @@ class TestBaseTest extends UnitTestCase {
|
|||
$this->assertEquals($length, strlen($string));
|
||||
// randomString() should always include an ampersand ('&') and a
|
||||
// greater than ('>') if $length is greater than 3.
|
||||
if ($length > 3) {
|
||||
if ($length > 4) {
|
||||
$this->assertContains('&', $string);
|
||||
$this->assertContains('>', $string);
|
||||
}
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* Contains \Drupal\system\Tests\Extension\ModuleHandlerTest.
|
||||
*/
|
||||
|
||||
namespace Drupal\system\Tests\Extension;
|
||||
namespace Drupal\Tests\system\Kernel\Extension;
|
||||
|
||||
use Drupal\Core\DependencyInjection\ContainerBuilder;
|
||||
use Drupal\simpletest\KernelTestBase;
|
||||
use \Drupal\Core\Extension\ModuleUninstallValidatorException;
|
||||
use Drupal\KernelTests\KernelTestBase;
|
||||
|
||||
/**
|
||||
* Tests ModuleHandler functionality.
|
||||
|
@ -21,10 +21,13 @@ class ModuleHandlerTest extends KernelTestBase {
|
|||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public static $modules = array('system');
|
||||
|
||||
public function setUp() {
|
||||
protected function setUp() {
|
||||
parent::setUp();
|
||||
|
||||
// @todo ModuleInstaller calls system_rebuild_module_data which is part of
|
||||
// system.module, see https://www.drupal.org/node/2208429.
|
||||
include_once $this->root . '/core/modules/system/system.module';
|
||||
|
||||
// Set up the state values so we know where to find the files when running
|
||||
// drupal_get_filename().
|
||||
// @todo Remove as part of https://www.drupal.org/node/2186491
|
||||
|
@ -34,8 +37,8 @@ class ModuleHandlerTest extends KernelTestBase {
|
|||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function containerBuild(ContainerBuilder $container) {
|
||||
parent::containerBuild($container);
|
||||
public function register(ContainerBuilder $container) {
|
||||
parent::register($container);
|
||||
// Put a fake route bumper on the container to be called during uninstall.
|
||||
$container
|
||||
->register('router.dumper', 'Drupal\Core\Routing\NullMatcherDumper');
|
||||
|
@ -45,24 +48,9 @@ class ModuleHandlerTest extends KernelTestBase {
|
|||
* The basic functionality of retrieving enabled modules.
|
||||
*/
|
||||
function testModuleList() {
|
||||
// Prime the drupal_get_filename() static cache with the location of the
|
||||
// testing profile as it is not the currently active profile and we don't
|
||||
// yet have any cached way to retrieve its location.
|
||||
// @todo Remove as part of https://www.drupal.org/node/2186491
|
||||
drupal_get_filename('profile', 'testing', 'core/profiles/testing/testing.info.yml');
|
||||
// Build a list of modules, sorted alphabetically.
|
||||
$profile_info = install_profile_info('testing', 'en');
|
||||
$module_list = $profile_info['dependencies'];
|
||||
$module_list = array();
|
||||
|
||||
// Installation profile is a module that is expected to be loaded.
|
||||
$module_list[] = 'testing';
|
||||
|
||||
sort($module_list);
|
||||
// Compare this list to the one returned by the module handler. We expect
|
||||
// them to match, since all default profile modules have a weight equal to 0
|
||||
// (except for block.module, which has a lower weight but comes first in
|
||||
// the alphabet anyway).
|
||||
$this->assertModuleList($module_list, 'Testing profile');
|
||||
$this->assertModuleList($module_list, 'Initial');
|
||||
|
||||
// Try to install a new module.
|
||||
$this->moduleInstaller()->install(array('ban'));
|
||||
|
@ -98,7 +86,6 @@ class ModuleHandlerTest extends KernelTestBase {
|
|||
protected function assertModuleList(Array $expected_values, $condition) {
|
||||
$expected_values = array_values(array_unique($expected_values));
|
||||
$enabled_modules = array_keys($this->container->get('module_handler')->getModuleList());
|
||||
$enabled_modules = sort($enabled_modules);
|
||||
$this->assertEqual($expected_values, $enabled_modules, format_string('@condition: extension handler returns correct results', array('@condition' => $condition)));
|
||||
}
|
||||
|
||||
|
@ -196,7 +183,7 @@ class ModuleHandlerTest extends KernelTestBase {
|
|||
function testUninstallProfileDependency() {
|
||||
$profile = 'minimal';
|
||||
$dependency = 'dblog';
|
||||
$this->settingsSet('install_profile', $profile);
|
||||
$this->setSetting('install_profile', $profile);
|
||||
// Prime the drupal_get_filename() static cache with the location of the
|
||||
// minimal profile as it is not the currently active profile and we don't
|
||||
// yet have any cached way to retrieve its location.
|
|
@ -5,14 +5,14 @@
|
|||
* Contains \Drupal\system\Tests\PhpStorage\PhpStorageFactoryTest.
|
||||
*/
|
||||
|
||||
namespace Drupal\system\Tests\PhpStorage;
|
||||
namespace Drupal\Tests\system\Kernel\PhpStorage;
|
||||
|
||||
use Drupal\Component\PhpStorage\MTimeProtectedFileStorage;
|
||||
use Drupal\Core\PhpStorage\PhpStorageFactory;
|
||||
use Drupal\Core\Site\Settings;
|
||||
use Drupal\Core\StreamWrapper\PublicStream;
|
||||
use Drupal\simpletest\KernelTestBase;
|
||||
use Drupal\system\PhpStorage\MockPhpStorage;
|
||||
use Drupal\KernelTests\KernelTestBase;
|
||||
|
||||
/**
|
||||
* Tests the PHP storage factory.
|
||||
|
@ -22,6 +22,18 @@ use Drupal\system\PhpStorage\MockPhpStorage;
|
|||
*/
|
||||
class PhpStorageFactoryTest extends KernelTestBase {
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected function setUp() {
|
||||
parent::setUp();
|
||||
|
||||
// Empty the PHP storage settings, as KernelTestBase sets it by default.
|
||||
$settings = Settings::getAll();
|
||||
unset($settings['php_storage']);
|
||||
new Settings($settings);
|
||||
}
|
||||
|
||||
/**
|
||||
* Tests the get() method with no settings.
|
||||
*/
|
||||
|
@ -59,7 +71,7 @@ class PhpStorageFactoryTest extends KernelTestBase {
|
|||
$this->setSettings('test', array('directory' => NULL));
|
||||
$php = PhpStorageFactory::get('test');
|
||||
$this->assertTrue($php instanceof MockPhpStorage, 'An MockPhpStorage instance was returned from overridden settings.');
|
||||
$this->assertIdentical(\Drupal::root() . '/' . PublicStream::basePath() . '/php', $php->getConfigurationValue('directory'), 'Default file directory was used.');
|
||||
$this->assertIdentical(PublicStream::basePath() . '/php', $php->getConfigurationValue('directory'), 'Default file directory was used.');
|
||||
|
||||
// Test that a default storage class is set if it's empty.
|
||||
$this->setSettings('test', array('class' => NULL));
|
|
@ -22,6 +22,16 @@
|
|||
<!-- Exclude Drush tests. -->
|
||||
<exclude>./drush/tests</exclude>
|
||||
</testsuite>
|
||||
<testsuite name="kernel">
|
||||
<directory>./tests/Drupal/KernelTests</directory>
|
||||
<directory>./modules/*/tests/src/Kernel</directory>
|
||||
<directory>../modules/*/tests/src/Kernel</directory>
|
||||
<directory>../sites/*/modules/*/tests/src/Kernel</directory>
|
||||
<!-- Exclude Composer's vendor directory so we don't run tests there. -->
|
||||
<exclude>./vendor</exclude>
|
||||
<!-- Exclude Drush tests. -->
|
||||
<exclude>./drush/tests</exclude>
|
||||
</testsuite>
|
||||
<testsuite name="functional">
|
||||
<directory>./tests/Drupal/FunctionalTests</directory>
|
||||
<directory>./modules/*/tests/src/Functional</directory>
|
||||
|
|
|
@ -709,7 +709,7 @@ function simpletest_script_command($test_id, $test_class) {
|
|||
* @see simpletest_script_run_one_test()
|
||||
*/
|
||||
function simpletest_script_cleanup($test_id, $test_class, $exitcode) {
|
||||
if (strpos($test_class, 'Drupal\\Tests\\') === 0) {
|
||||
if (is_subclass_of($test_class, '\PHPUnit_Framework_TestCase')) {
|
||||
// PHPUnit test, move on.
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -0,0 +1,129 @@
|
|||
<?php
|
||||
|
||||
/**
|
||||
* @file
|
||||
* Contains \Drupal\KernelTests\AssertLegacyTrait.
|
||||
*/
|
||||
|
||||
namespace Drupal\KernelTests;
|
||||
|
||||
/**
|
||||
* Translates Simpletest assertion methods to PHPUnit.
|
||||
*
|
||||
* Protected methods are custom. Public static methods override methods of
|
||||
* \PHPUnit_Framework_Assert.
|
||||
*
|
||||
* @deprecated Scheduled for removal in Drupal 9.0.0. Use PHPUnit's native
|
||||
* assert methods instead.
|
||||
*/
|
||||
trait AssertLegacyTrait {
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::assert()
|
||||
*
|
||||
* @deprecated Scheduled for removal in Drupal 9.0.0. Use self::assertTrue()
|
||||
* instead.
|
||||
*/
|
||||
protected function assert($actual, $message = '') {
|
||||
parent::assertTrue((bool) $actual, $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::assertTrue()
|
||||
*/
|
||||
public static function assertTrue($actual, $message = '') {
|
||||
if (is_bool($actual)) {
|
||||
parent::assertTrue($actual, $message);
|
||||
}
|
||||
else {
|
||||
parent::assertNotEmpty($actual, $message);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::assertFalse()
|
||||
*/
|
||||
public static function assertFalse($actual, $message = '') {
|
||||
if (is_bool($actual)) {
|
||||
parent::assertFalse($actual, $message);
|
||||
}
|
||||
else {
|
||||
parent::assertEmpty($actual, $message);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::assertEqual()
|
||||
*
|
||||
* @deprecated Scheduled for removal in Drupal 9.0.0. Use self::assertEquals()
|
||||
* instead.
|
||||
*/
|
||||
protected function assertEqual($actual, $expected, $message = '') {
|
||||
$this->assertEquals($expected, $actual, $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::assertNotEqual()
|
||||
*
|
||||
* @deprecated Scheduled for removal in Drupal 9.0.0. Use
|
||||
* self::assertNotEquals() instead.
|
||||
*/
|
||||
protected function assertNotEqual($actual, $expected, $message = '') {
|
||||
$this->assertNotEquals($expected, $actual, $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::assertIdentical()
|
||||
*
|
||||
* @deprecated Scheduled for removal in Drupal 9.0.0. Use self::assertSame()
|
||||
* instead.
|
||||
*/
|
||||
protected function assertIdentical($actual, $expected, $message = '') {
|
||||
$this->assertSame($expected, $actual, $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::assertNotIdentical()
|
||||
*
|
||||
* @deprecated Scheduled for removal in Drupal 9.0.0. Use
|
||||
* self::assertNotSame() instead.
|
||||
*/
|
||||
protected function assertNotIdentical($actual, $expected, $message = '') {
|
||||
$this->assertNotSame($expected, $actual, $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::assertIdenticalObject()
|
||||
*
|
||||
* @deprecated Scheduled for removal in Drupal 9.0.0. Use self::assertEquals()
|
||||
* instead.
|
||||
*/
|
||||
protected function assertIdenticalObject($actual, $expected, $message = '') {
|
||||
// Note: ::assertSame checks whether its the same object. ::assertEquals
|
||||
// though compares
|
||||
|
||||
$this->assertEquals($expected, $actual, $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::pass()
|
||||
*
|
||||
* @deprecated Scheduled for removal in Drupal 9.0.0. Use self::assertTrue()
|
||||
* instead.
|
||||
*/
|
||||
protected function pass($message) {
|
||||
$this->assertTrue(TRUE, $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @see \Drupal\simpletest\TestBase::verbose()
|
||||
*/
|
||||
protected function verbose($message) {
|
||||
if (in_array('--debug', $_SERVER['argv'], TRUE)) {
|
||||
// Write directly to STDOUT to not produce unexpected test output.
|
||||
// The STDOUT stream does not obey output buffering.
|
||||
fwrite(STDOUT, $message . "\n");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,219 @@
|
|||
<?php
|
||||
|
||||
/**
|
||||
* @file
|
||||
* Contains \Drupal\KernelTests\KernelTestBaseTest.
|
||||
*/
|
||||
|
||||
namespace Drupal\KernelTests;
|
||||
|
||||
use org\bovigo\vfs\vfsStream;
|
||||
use org\bovigo\vfs\visitor\vfsStreamStructureVisitor;
|
||||
|
||||
/**
|
||||
* @coversDefaultClass \Drupal\KernelTests\KernelTestBase
|
||||
* @group PHPUnit
|
||||
*/
|
||||
class KernelTestBaseTest extends KernelTestBase {
|
||||
|
||||
/**
|
||||
* @covers ::setUpBeforeClass
|
||||
*/
|
||||
public function testSetUpBeforeClass() {
|
||||
// Note: PHPUnit automatically restores the original working directory.
|
||||
$this->assertSame(realpath(__DIR__ . '/../../../../'), getcwd());
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::bootEnvironment
|
||||
*/
|
||||
public function testBootEnvironment() {
|
||||
$this->assertRegExp('/^simpletest\d{6}$/', $this->databasePrefix);
|
||||
$this->assertStringStartsWith('vfs://root/sites/simpletest/', $this->siteDirectory);
|
||||
$this->assertEquals(array(
|
||||
'root' => array(
|
||||
'sites' => array(
|
||||
'simpletest' => array(
|
||||
substr($this->databasePrefix, 10) => array(
|
||||
'files' => array(
|
||||
'config' => array(
|
||||
'active' => array(),
|
||||
'staging' => array(),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
), vfsStream::inspect(new vfsStreamStructureVisitor())->getStructure());
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::getDatabaseConnectionInfo
|
||||
*/
|
||||
public function testGetDatabaseConnectionInfoWithOutManualSetDbUrl() {
|
||||
$this->setUp();
|
||||
|
||||
$options = $this->container->get('database')->getConnectionOptions();
|
||||
$this->assertSame($this->databasePrefix, $options['prefix']['default']);
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::getDatabaseConnectionInfo
|
||||
*/
|
||||
public function testGetDatabaseConnectionInfoWithManualSetDbUrl() {
|
||||
if (!file_exists('/tmp')) {
|
||||
$this->markTestSkipped();
|
||||
}
|
||||
putenv('SIMPLETEST_DB=sqlite://localhost//tmp/test2.sqlite');
|
||||
$this->setUp();
|
||||
|
||||
$options = $this->container->get('database')->getConnectionOptions();
|
||||
$this->assertNotEqual('', $options['prefix']['default']);
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::setUp
|
||||
*/
|
||||
public function testSetUp() {
|
||||
$this->assertTrue($this->container->has('request_stack'));
|
||||
$this->assertTrue($this->container->initialized('request_stack'));
|
||||
$request = $this->container->get('request_stack')->getCurrentRequest();
|
||||
$this->assertNotEmpty($request);
|
||||
$this->assertEquals('/', $request->getPathInfo());
|
||||
|
||||
$this->assertSame($request, \Drupal::request());
|
||||
|
||||
$this->assertEquals($this, $GLOBALS['conf']['container_service_providers']['test']);
|
||||
|
||||
$GLOBALS['destroy-me'] = TRUE;
|
||||
$this->assertArrayHasKey('destroy-me', $GLOBALS);
|
||||
|
||||
$schema = $this->container->get('database')->schema();
|
||||
$schema->createTable('foo', array(
|
||||
'fields' => array(
|
||||
'number' => array(
|
||||
'type' => 'int',
|
||||
'unsigned' => TRUE,
|
||||
'not null' => TRUE,
|
||||
),
|
||||
),
|
||||
));
|
||||
$this->assertTrue($schema->tableExists('foo'));
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::setUp
|
||||
* @depends testSetUp
|
||||
*/
|
||||
public function testSetUpDoesNotLeak() {
|
||||
$this->assertArrayNotHasKey('destroy-me', $GLOBALS);
|
||||
|
||||
// Ensure that we have a different database prefix.
|
||||
$schema = $this->container->get('database')->schema();
|
||||
$this->assertFalse($schema->tableExists('foo'));
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::register
|
||||
*/
|
||||
public function testRegister() {
|
||||
// Verify that this container is identical to the actual container.
|
||||
$this->assertInstanceOf('Symfony\Component\DependencyInjection\ContainerInterface', $this->container);
|
||||
$this->assertSame($this->container, \Drupal::getContainer());
|
||||
|
||||
// The request service should never exist.
|
||||
$this->assertFalse($this->container->has('request'));
|
||||
|
||||
// Verify that there is a request stack.
|
||||
$request = $this->container->get('request_stack')->getCurrentRequest();
|
||||
$this->assertInstanceOf('Symfony\Component\HttpFoundation\Request', $request);
|
||||
$this->assertSame($request, \Drupal::request());
|
||||
|
||||
// Trigger a container rebuild.
|
||||
$this->enableModules(array('system'));
|
||||
|
||||
// Verify that this container is identical to the actual container.
|
||||
$this->assertInstanceOf('Symfony\Component\DependencyInjection\ContainerInterface', $this->container);
|
||||
$this->assertSame($this->container, \Drupal::getContainer());
|
||||
|
||||
// The request service should never exist.
|
||||
$this->assertFalse($this->container->has('request'));
|
||||
|
||||
// Verify that there is a request stack (and that it persisted).
|
||||
$new_request = $this->container->get('request_stack')->getCurrentRequest();
|
||||
$this->assertInstanceOf('Symfony\Component\HttpFoundation\Request', $new_request);
|
||||
$this->assertSame($new_request, \Drupal::request());
|
||||
$this->assertSame($request, $new_request);
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::getCompiledContainerBuilder
|
||||
*
|
||||
* The point of this test is to have integration level testing.
|
||||
*/
|
||||
public function testCompiledContainer() {
|
||||
$this->enableModules(['system', 'user']);
|
||||
$this->assertNull($this->installConfig('user'));
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::getCompiledContainerBuilder
|
||||
* @depends testCompiledContainer
|
||||
*
|
||||
* The point of this test is to have integration level testing.
|
||||
*/
|
||||
public function testCompiledContainerIsDestructed() {
|
||||
$this->enableModules(['system', 'user']);
|
||||
$this->assertNull($this->installConfig('user'));
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::render
|
||||
*/
|
||||
public function testRender() {
|
||||
$type = 'processed_text';
|
||||
$element_info = $this->container->get('element_info');
|
||||
$this->assertSame(['#defaults_loaded' => TRUE], $element_info->getInfo($type));
|
||||
|
||||
$this->enableModules(array('filter'));
|
||||
|
||||
$this->assertNotSame($element_info, $this->container->get('element_info'));
|
||||
$this->assertNotEmpty($this->container->get('element_info')->getInfo($type));
|
||||
|
||||
$build = array(
|
||||
'#type' => 'html_tag',
|
||||
'#tag' => 'h3',
|
||||
'#value' => 'Inner',
|
||||
);
|
||||
$expected = "<h3>Inner</h3>\n";
|
||||
|
||||
$this->assertEquals('core', \Drupal::theme()->getActiveTheme()->getName());
|
||||
$output = \Drupal::service('renderer')->renderRoot($build);
|
||||
$this->assertEquals('core', \Drupal::theme()->getActiveTheme()->getName());
|
||||
|
||||
$this->assertEquals($expected, $build['#children']);
|
||||
$this->assertEquals($expected, $output);
|
||||
}
|
||||
|
||||
/**
|
||||
* @covers ::render
|
||||
*/
|
||||
public function testRenderWithTheme() {
|
||||
$this->enableModules(array('system'));
|
||||
|
||||
$build = array(
|
||||
'#type' => 'textfield',
|
||||
'#name' => 'test',
|
||||
);
|
||||
$expected = '/' . preg_quote('<input type="text" name="test"', '/') . '/';
|
||||
|
||||
$this->assertArrayNotHasKey('theme', $GLOBALS);
|
||||
$output = \Drupal::service('renderer')->renderRoot($build);
|
||||
$this->assertEquals('core', \Drupal::theme()->getActiveTheme()->getName());
|
||||
|
||||
$this->assertRegExp($expected, (string) $build['#children']);
|
||||
$this->assertRegExp($expected, (string) $output);
|
||||
}
|
||||
|
||||
}
|
|
@ -20,9 +20,10 @@ function drupal_phpunit_find_extension_directories($scan_directory) {
|
|||
$extensions = array();
|
||||
$dirs = new \RecursiveIteratorIterator(new \RecursiveDirectoryIterator($scan_directory, \RecursiveDirectoryIterator::FOLLOW_SYMLINKS));
|
||||
foreach ($dirs as $dir) {
|
||||
if (strpos($dir->getPathname(), 'info.yml') !== FALSE) {
|
||||
if (strpos($dir->getPathname(), '.info.yml') !== FALSE) {
|
||||
// Cut off ".info.yml" from the filename for use as the extension name.
|
||||
$extensions[substr($dir->getFilename(), 0, -9)] = $dir->getPathInfo()->getRealPath();
|
||||
$extensions[substr($dir->getFilename(), 0, -9)] = $dir->getPathInfo()
|
||||
->getRealPath();
|
||||
}
|
||||
}
|
||||
return $extensions;
|
||||
|
@ -35,10 +36,19 @@ function drupal_phpunit_find_extension_directories($scan_directory) {
|
|||
* An array of directories under which contributed extensions may exist.
|
||||
*/
|
||||
function drupal_phpunit_contrib_extension_directory_roots() {
|
||||
$sites_path = __DIR__ . '/../../sites';
|
||||
$paths = array();
|
||||
$root = dirname(dirname(__DIR__));
|
||||
$paths = array(
|
||||
$root . '/core/modules',
|
||||
$root . '/core/profiles',
|
||||
$root . '/modules',
|
||||
$root . '/profiles',
|
||||
);
|
||||
$sites_path = $root . '/sites';
|
||||
// Note this also checks sites/../modules and sites/../profiles.
|
||||
foreach (scandir($sites_path) as $site) {
|
||||
if ($site[0] === '.' || $site === 'simpletest') {
|
||||
continue;
|
||||
}
|
||||
$path = "$sites_path/$site";
|
||||
$paths[] = is_dir("$path/modules") ? realpath("$path/modules") : NULL;
|
||||
$paths[] = is_dir("$path/profiles") ? realpath("$path/profiles") : NULL;
|
||||
|
@ -49,37 +59,43 @@ function drupal_phpunit_contrib_extension_directory_roots() {
|
|||
/**
|
||||
* Registers the namespace for each extension directory with the autoloader.
|
||||
*
|
||||
* @param Composer\Autoload\ClassLoader $loader
|
||||
* The supplied autoloader.
|
||||
* @param array $dirs
|
||||
* An associative array of extension directories, keyed by extension name.
|
||||
*
|
||||
* @return array
|
||||
* An associative array of extension directories, keyed by their namespace.
|
||||
*/
|
||||
function drupal_phpunit_register_extension_dirs(Composer\Autoload\ClassLoader $loader, $dirs) {
|
||||
function drupal_phpunit_get_extension_namespaces($dirs) {
|
||||
$namespaces = array();
|
||||
foreach ($dirs as $extension => $dir) {
|
||||
if (is_dir($dir . '/src')) {
|
||||
// Register the PSR-4 directory for module-provided classes.
|
||||
$loader->addPsr4('Drupal\\' . $extension . '\\', $dir . '/src');
|
||||
$namespaces['Drupal\\' . $extension . '\\'][] = $dir . '/src';
|
||||
}
|
||||
if (is_dir($dir . '/tests/src')) {
|
||||
// Register the PSR-4 directory for PHPUnit test classes.
|
||||
$loader->addPsr4('Drupal\\Tests\\' . $extension . '\\', $dir . '/tests/src');
|
||||
$namespaces['Drupal\\Tests\\' . $extension . '\\'][] = $dir . '/tests/src';
|
||||
}
|
||||
}
|
||||
return $namespaces;
|
||||
}
|
||||
|
||||
// Start with classes in known locations.
|
||||
$loader = require __DIR__ . '/../../autoload.php';
|
||||
$loader->add('Drupal\\Tests', __DIR__);
|
||||
$loader->add('Drupal\\KernelTests', __DIR__);
|
||||
|
||||
// Scan for arbitrary extension namespaces from core and contrib.
|
||||
$extension_roots = array_merge(array(
|
||||
__DIR__ . '/../modules',
|
||||
__DIR__ . '/../profiles',
|
||||
), drupal_phpunit_contrib_extension_directory_roots());
|
||||
if (!isset($GLOBALS['namespaces'])) {
|
||||
// Scan for arbitrary extension namespaces from core and contrib.
|
||||
$extension_roots = drupal_phpunit_contrib_extension_directory_roots();
|
||||
|
||||
$dirs = array_map('drupal_phpunit_find_extension_directories', $extension_roots);
|
||||
$dirs = array_reduce($dirs, 'array_merge', array());
|
||||
drupal_phpunit_register_extension_dirs($loader, $dirs);
|
||||
$dirs = array_map('drupal_phpunit_find_extension_directories', $extension_roots);
|
||||
$dirs = array_reduce($dirs, 'array_merge', array());
|
||||
$GLOBALS['namespaces'] = drupal_phpunit_get_extension_namespaces($dirs);
|
||||
}
|
||||
foreach ($GLOBALS['namespaces'] as $prefix => $paths) {
|
||||
$loader->addPsr4($prefix, $paths);
|
||||
}
|
||||
|
||||
// Set sane locale settings, to ensure consistent string, dates, times and
|
||||
// numbers handling.
|
||||
|
|
Loading…
Reference in New Issue