Commit 463fd530 authored by alexpott's avatar alexpott

Issue #2270815 by vijaycs85, Gábor Hojtsy, nvinayvinay: Make schema testing...

Issue #2270815 by vijaycs85, Gábor Hojtsy, nvinayvinay: Make schema testing code available as generic API.
parent f39f2c27
......@@ -2,26 +2,22 @@
/**
* @file
* Contains Drupal\config\Tests\ConfigSchemaTestBase.
* Contains \Drupal\Core\Config\Schema\SchemaCheckTrait.
*/
namespace Drupal\config\Tests;
namespace Drupal\Core\Config\Schema;
use Drupal\Core\Config\Schema\ArrayElement;
use Drupal\Core\Config\TypedConfigManagerInterface;
use Drupal\Core\TypedData\PrimitiveInterface;
use Drupal\Core\TypedData\Type\BooleanInterface;
use Drupal\Core\TypedData\Type\StringInterface;
use Drupal\Component\Utility\String;
use Drupal\Core\Config\Schema\SchemaIncompleteException;
use Drupal\Core\TypedData\PrimitiveInterface;
use Drupal\Core\TypedData\Type\FloatInterface;
use Drupal\Core\TypedData\Type\IntegerInterface;
use Drupal\simpletest\WebTestBase;
/**
* Provides a base class to help test configuration schema.
* Provides a trait for checking configuration schema.
*/
abstract class ConfigSchemaTestBase extends WebTestBase {
trait SchemaCheckTrait {
/**
* The config schema wrapper object for the configuration object under test.
......@@ -38,14 +34,7 @@ abstract class ConfigSchemaTestBase extends WebTestBase {
protected $configName;
/**
* Global state for whether the config has a valid schema.
*
* @var boolean
*/
protected $configPass;
/**
* Asserts the TypedConfigManager has a valid schema for the configuration.
* Checks the TypedConfigManager has a valid schema for the configuration.
*
* @param \Drupal\Core\Config\TypedConfigManagerInterface $typed_config
* The TypedConfigManager.
......@@ -53,22 +42,25 @@ abstract class ConfigSchemaTestBase extends WebTestBase {
* The configuration name.
* @param array $config_data
* The configuration data.
*
* @return array|bool
* FALSE if no schema found. List of errors if any found. TRUE if fully
* valid.
*/
public function assertConfigSchema(TypedConfigManagerInterface $typed_config, $config_name, $config_data) {
public function checkConfigSchema(TypedConfigManagerInterface $typed_config, $config_name, $config_data) {
$this->configName = $config_name;
if (!$typed_config->hasConfigSchema($config_name)) {
$this->fail(String::format('No schema for !config_name', array('!config_name' => $config_name)));
return;
return FALSE;
}
$definition = $typed_config->getDefinition($config_name);
$this->schema = $typed_config->create($definition, $config_data);
$this->configPass = TRUE;
foreach ($config_data as $key => $value) {
$this->checkValue($key, $value);
$errors = $this->checkValue($key, $value);
}
if ($this->configPass) {
$this->pass(String::format('Schema found for !config_name and values comply with schema.', array('!config_name' => $config_name)));
if (empty($errors)) {
return TRUE;
}
return $errors;
}
/**
......@@ -79,25 +71,26 @@ public function assertConfigSchema(TypedConfigManagerInterface $typed_config, $c
* @param mixed $value
* Value of given key.
*
* @return mixed
* Returns mixed value.
* @return array
* List of errors found while checking with the corresponding schema.
*/
protected function checkValue($key, $value) {
$error_key = $this->configName . ':' . $key;
$element = FALSE;
try {
$element = $this->schema->get($key);
}
catch (SchemaIncompleteException $e) {
if (is_scalar($value) || $value === NULL) {
$this->fail("{$this->configName}:$key has no schema.");
return array($error_key => 'Missing schema.');
}
}
// Do not check value if it is defined to be ignored.
if ($element && $element instanceof Ignore) {
return $value;
return array();
}
if (is_scalar($value) || $value === NULL) {
if ($element && is_scalar($value) || $value === NULL) {
$success = FALSE;
$type = gettype($value);
if ($element instanceof PrimitiveInterface) {
......@@ -111,12 +104,13 @@ protected function checkValue($key, $value) {
}
$class = get_class($element);
if (!$success) {
$this->fail("{$this->configName}:$key has the wrong schema. Variable type is $type and schema class is $class.");
return array($error_key => "Variable type is $type but applied schema class is $class.");
}
}
else {
$errors = array();
if (!$element instanceof ArrayElement) {
$this->fail("Non-scalar {$this->configName}:$key is not defined as an array type (such as mapping or sequence).");
$errors[$error_key] = 'Non-scalar value but not defined as an array (such as mapping or sequence)';
}
// Go on processing so we can get errors on all levels. Any non-scalar
......@@ -126,18 +120,11 @@ protected function checkValue($key, $value) {
}
// Recurse into any nested keys.
foreach ($value as $nested_value_key => $nested_value) {
$value[$nested_value_key] = $this->checkValue($key . '.' . $nested_value_key, $nested_value);
$errors = array_merge($errors, $this->checkValue($key . '.' . $nested_value_key, $nested_value));
}
return $errors;
}
return $value;
}
/**
* {@inheritdoc}
*/
protected function fail($message = NULL, $group = 'Other') {
$this->configPass = FALSE;
return parent::fail($message, $group);
// No errors found.
return array();
}
}
......@@ -8,12 +8,15 @@
namespace Drupal\block\Tests;
use Drupal\block\Entity\Block;
use Drupal\config\Tests\ConfigSchemaTestBase;
use Drupal\config\Tests\SchemaCheckTestTrait;
use Drupal\simpletest\WebTestBase;
/**
* Tests the block config schema.
*/
class BlockConfigSchemaTest extends ConfigSchemaTestBase {
class BlockConfigSchemaTest extends WebTestBase {
use SchemaCheckTestTrait;
/**
* {@inheritdoc}
......
......@@ -7,12 +7,15 @@
namespace Drupal\color\Tests;
use Drupal\config\Tests\ConfigSchemaTestBase;
use Drupal\config\Tests\SchemaCheckTestTrait;
use Drupal\simpletest\WebTestBase;
/**
* Tests the Color config schema.
*/
class ColorConfigSchemaTest extends ConfigSchemaTestBase {
class ColorConfigSchemaTest extends WebTestBase {
use SchemaCheckTestTrait;
/**
* Modules to enable.
......
......@@ -10,11 +10,14 @@
use Drupal\config_test\TestInstallStorage;
use Drupal\Core\Config\InstallStorage;
use Drupal\Core\Config\TypedConfigManager;
use Drupal\simpletest\WebTestBase;
/**
* Tests default configuration availability and type with configuration schema.
*/
class DefaultConfigTest extends ConfigSchemaTestBase {
class DefaultConfigTest extends WebTestBase {
use SchemaCheckTestTrait;
/**
* Modules to enable.
......
<?php
/**
* @file
* Contains Drupal\config\Tests\SchemaCheckTestTrait.
*/
namespace Drupal\config\Tests;
use Drupal\Core\Config\TypedConfigManagerInterface;
use Drupal\Core\Config\Schema\SchemaCheckTrait;
use Drupal\Component\Utility\String;
/**
* Provides a class for checking configuration schema.
*/
trait SchemaCheckTestTrait {
use SchemaCheckTrait;
/**
* Asserts the TypedConfigManager has a valid schema for the configuration.
*
* @param \Drupal\Core\Config\TypedConfigManagerInterface $typed_config
* The TypedConfigManager.
* @param string $config_name
* The configuration name.
* @param array $config_data
* The configuration data.
*/
public function assertConfigSchema(TypedConfigManagerInterface $typed_config, $config_name, $config_data) {
$errors = $this->checkConfigSchema($typed_config, $config_name, $config_data);
if ($errors === FALSE) {
// @todo Since the use of this trait is under TestBase, it works.
// Can be fixed as part of https://drupal.org/node/2260053.
$this->fail(String::format('No schema for !config_name', array('!config_name' => $config_name)));
return;
}
elseif ($errors === TRUE) {
// @todo Since the use of this trait is under TestBase, it works.
// Can be fixed as part of https://drupal.org/node/2260053.
$this->pass(String::format('Schema found for !config_name and values comply with schema.', array('!config_name' => $config_name)));
}
else {
foreach ($errors as $key => $error) {
// @todo Since the use of this trait is under TestBase, it works.
// Can be fixed as part of https://drupal.org/node/2260053.
$this->fail($key . ': ' . $error);
}
}
}
}
......@@ -7,12 +7,15 @@
namespace Drupal\language\Tests;
use Drupal\config\Tests\ConfigSchemaTestBase;
use Drupal\config\Tests\SchemaCheckTestTrait;
use Drupal\simpletest\WebTestBase;
/**
* Tests the language config schema.
*/
class LanguageConfigSchemaTest extends ConfigSchemaTestBase {
class LanguageConfigSchemaTest extends WebTestBase {
use SchemaCheckTestTrait;
/**
* Modules to enable.
......
......@@ -7,12 +7,15 @@
namespace Drupal\user\Tests;
use Drupal\config\Tests\ConfigSchemaTestBase;
use Drupal\config\Tests\SchemaCheckTestTrait;
use Drupal\simpletest\WebTestBase;
/**
* Tests the User action config schema.
*/
class UserActionConfigSchemaTest extends ConfigSchemaTestBase {
class UserActionConfigSchemaTest extends WebTestBase {
use SchemaCheckTestTrait;
/**
* Modules to enable.
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment