Issue #3462156 by niklan, vensires, smustgrave, quietone, wim leers: Throw an exception if a component property's `type` contains non-string values
parent
833e599d18
commit
f0b4dd2ba4
|
@ -81,6 +81,28 @@ class ComponentValidator {
|
|||
if (($schema['properties'] ?? NULL) === []) {
|
||||
$schema['properties'] = new \stdClass();
|
||||
}
|
||||
|
||||
// Ensure that all property types are strings. For example, a null value
|
||||
// will not automatically convert to 'null', which will lead to a PHP error
|
||||
// that is hard to trace back to the property.
|
||||
$non_string_props = [];
|
||||
\array_walk($prop_names, function (string $prop) use (&$non_string_props, $schema) {
|
||||
$type = $schema['properties'][$prop]['type'];
|
||||
$types = !\is_array($type) ? [$type] : $type;
|
||||
$non_string_types = \array_filter($types, static fn (mixed $type) => !\is_string($type));
|
||||
if ($non_string_types) {
|
||||
$non_string_props[] = $prop;
|
||||
}
|
||||
});
|
||||
|
||||
if ($non_string_props) {
|
||||
throw new InvalidComponentException(\sprintf(
|
||||
'The component "%s" uses non-string types for properties: %s.',
|
||||
$definition['id'],
|
||||
\implode(', ', $non_string_props),
|
||||
));
|
||||
}
|
||||
|
||||
$classes_per_prop = $this->getClassProps($schema);
|
||||
$missing_class_errors = [];
|
||||
foreach ($classes_per_prop as $prop_name => $class_types) {
|
||||
|
|
|
@ -65,24 +65,43 @@ class ComponentValidatorTest extends TestCase {
|
|||
/**
|
||||
* Data provider with invalid component definitions.
|
||||
*
|
||||
* @return array
|
||||
* The data.
|
||||
* @return \Generator
|
||||
* Returns the generator with the invalid definitions.
|
||||
*/
|
||||
public static function dataProviderValidateDefinitionInvalid(): array {
|
||||
public static function dataProviderValidateDefinitionInvalid(): \Generator {
|
||||
$valid_cta = static::loadComponentDefinitionFromFs('my-cta');
|
||||
|
||||
$cta_with_missing_required = $valid_cta;
|
||||
unset($cta_with_missing_required['path']);
|
||||
yield 'missing required' => [$cta_with_missing_required];
|
||||
|
||||
$cta_with_invalid_class = $valid_cta;
|
||||
$cta_with_invalid_class['props']['properties']['attributes']['type'] = 'Drupal\Foo\Invalid';
|
||||
yield 'invalid class' => [$cta_with_invalid_class];
|
||||
|
||||
$cta_with_invalid_enum = array_merge(
|
||||
$valid_cta,
|
||||
['extension_type' => 'invalid'],
|
||||
);
|
||||
return [
|
||||
[$cta_with_missing_required],
|
||||
[$cta_with_invalid_class],
|
||||
[$cta_with_invalid_enum],
|
||||
];
|
||||
yield 'invalid enum' => [$cta_with_invalid_enum];
|
||||
|
||||
// A list of property types that are not strings, but can be provided via
|
||||
// YAML.
|
||||
$non_string_types = [NULL, 123, 123.45, TRUE];
|
||||
foreach ($non_string_types as $non_string_type) {
|
||||
$cta_with_non_string_prop_type = $valid_cta;
|
||||
$cta_with_non_string_prop_type['props']['properties']['text']['type'] = $non_string_type;
|
||||
yield "non string type ($non_string_type)" => [$cta_with_non_string_prop_type];
|
||||
|
||||
// Same, but as a part of the list of allowed types.
|
||||
$cta_with_non_string_prop_type['props']['properties']['text']['type'] = ['string', $non_string_type];
|
||||
yield "non string type ($non_string_type) in a list of types" => [$cta_with_non_string_prop_type];
|
||||
}
|
||||
|
||||
// The array is a valid value for the 'type' parameter, but it is not
|
||||
// allowed as the allowed type.
|
||||
$cta_with_non_string_prop_type['props']['properties']['text']['type'] = ['string', []];
|
||||
yield 'non string type (Array)' => [$cta_with_non_string_prop_type];
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
Loading…
Reference in New Issue