Skip to content

Commit 82a7602

Browse files
committed
Added array tuple validation
Optimized string exceptions Removed unused code
1 parent c743cec commit 82a7602

20 files changed

+379
-76
lines changed

src/Model/Property/Property.php

Lines changed: 0 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,6 @@ class Property implements PropertyInterface
3434

3535
/** @var Validator[] */
3636
protected $validator = [];
37-
/** @var Property[] */
38-
protected $nestedProperties = [];
3937
/** @var Schema */
4038
protected $schema;
4139
/** @var PropertyDecoratorInterface[] */
@@ -183,24 +181,6 @@ function (Validator $validator) {
183181
);
184182
}
185183

186-
/**
187-
* @inheritdoc
188-
*/
189-
public function getNestedProperties(): array
190-
{
191-
return $this->nestedProperties;
192-
}
193-
194-
/**
195-
* @inheritdoc
196-
*/
197-
public function addNestedProperty(PropertyInterface $nestedProperty): PropertyInterface
198-
{
199-
$this->nestedProperties[] = $nestedProperty;
200-
201-
return $this;
202-
}
203-
204184
/**
205185
* @inheritdoc
206186
*/

src/Model/Property/PropertyInterface.php

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -98,18 +98,6 @@ public function filterValidators(callable $filter): PropertyInterface;
9898
*/
9999
public function getOrderedValidators(): array;
100100

101-
/**
102-
* @return PropertyInterface[]
103-
*/
104-
public function getNestedProperties(): array;
105-
106-
/**
107-
* @param PropertyInterface $nestedProperty
108-
*
109-
* @return PropertyInterface
110-
*/
111-
public function addNestedProperty(PropertyInterface $nestedProperty): PropertyInterface;
112-
113101
/**
114102
* Add a decorator to the property
115103
*

src/Model/Property/PropertyProxy.php

Lines changed: 0 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -140,22 +140,6 @@ public function getOrderedValidators(): array
140140
return $this->getProperty()->getOrderedValidators();
141141
}
142142

143-
/**
144-
* @inheritdoc
145-
*/
146-
public function getNestedProperties(): array
147-
{
148-
return $this->getProperty()->getNestedProperties();
149-
}
150-
151-
/**
152-
* @inheritdoc
153-
*/
154-
public function addNestedProperty(PropertyInterface $nestedProperty): PropertyInterface
155-
{
156-
return $this->getProperty()->addNestedProperty($nestedProperty);
157-
}
158-
159143
/**
160144
* @inheritdoc
161145
*/

src/Model/Validator/AdditionalPropertiesValidator.php

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -20,14 +20,14 @@
2020
*
2121
* @package PHPModelGenerator\Model\Validator
2222
*/
23-
class AdditionalPropertiesValidator extends AbstractComposedPropertyValidator
23+
class AdditionalPropertiesValidator extends PropertyTemplateValidator
2424
{
2525
/**
2626
* AdditionalPropertiesValidator constructor.
2727
*
2828
* @param SchemaProcessor $schemaProcessor
2929
* @param Schema $schema
30-
* @param array $propertyStructure
30+
* @param array $tuplePropertiesStructure
3131
*
3232
* @throws FileSystemException
3333
* @throws SchemaException
@@ -37,7 +37,7 @@ class AdditionalPropertiesValidator extends AbstractComposedPropertyValidator
3737
public function __construct(
3838
SchemaProcessor $schemaProcessor,
3939
Schema $schema,
40-
array $propertyStructure
40+
array $tuplePropertiesStructure
4141
) {
4242
$propertyFactory = new PropertyFactory(new PropertyProcessorFactory());
4343

@@ -46,7 +46,7 @@ public function __construct(
4646
$schemaProcessor,
4747
$schema,
4848
'additional property',
49-
$propertyStructure['additionalProperties']
49+
$tuplePropertiesStructure['additionalProperties']
5050
);
5151

5252
parent::__construct(
@@ -60,7 +60,7 @@ public function __construct(
6060
'additionalProperties' => preg_replace(
6161
'(\d+\s=>)',
6262
'',
63-
var_export(array_keys($propertyStructure['properties'] ?? []), true)
63+
var_export(array_keys($tuplePropertiesStructure['properties'] ?? []), true)
6464
),
6565
'generatorConfiguration' => $schemaProcessor->getGeneratorConfiguration(),
6666
'viewHelper' => new RenderHelper($schemaProcessor->getGeneratorConfiguration()),
Lines changed: 81 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,81 @@
1+
<?php
2+
3+
declare(strict_types = 1);
4+
5+
namespace PHPModelGenerator\Model\Validator;
6+
7+
use PHPMicroTemplate\Exception\FileSystemException;
8+
use PHPMicroTemplate\Exception\SyntaxErrorException;
9+
use PHPMicroTemplate\Exception\UndefinedSymbolException;
10+
use PHPModelGenerator\Exception\SchemaException;
11+
use PHPModelGenerator\Model\Schema;
12+
use PHPModelGenerator\PropertyProcessor\PropertyCollectionProcessor;
13+
use PHPModelGenerator\PropertyProcessor\PropertyFactory;
14+
use PHPModelGenerator\PropertyProcessor\PropertyProcessorFactory;
15+
use PHPModelGenerator\SchemaProcessor\SchemaProcessor;
16+
use PHPModelGenerator\Utils\RenderHelper;
17+
18+
/**
19+
* Class ArrayTupleValidator
20+
*
21+
* @package PHPModelGenerator\Model\Validator
22+
*/
23+
class ArrayTupleValidator extends PropertyTemplateValidator
24+
{
25+
/**
26+
* ArrayTupleValidator constructor.
27+
*
28+
* @param SchemaProcessor $schemaProcessor
29+
* @param Schema $schema
30+
* @param array $tuplePropertiesStructure
31+
* @param string $propertyName
32+
*
33+
* @throws SchemaException
34+
* @throws FileSystemException
35+
* @throws SyntaxErrorException
36+
* @throws UndefinedSymbolException
37+
*/
38+
public function __construct(
39+
SchemaProcessor $schemaProcessor,
40+
Schema $schema,
41+
array $tuplePropertiesStructure,
42+
string $propertyName
43+
) {
44+
$propertyFactory = new PropertyFactory(new PropertyProcessorFactory());
45+
46+
$tupleProperties = [];
47+
foreach ($tuplePropertiesStructure as $tupleIndex => $tupleItem) {
48+
// an item of the array behaves like a nested property to add item-level validation
49+
$tupleProperties[] = $propertyFactory->create(
50+
new PropertyCollectionProcessor(),
51+
$schemaProcessor,
52+
$schema,
53+
"tuple item #$tupleIndex of array {$propertyName}",
54+
$tupleItem
55+
);
56+
}
57+
58+
parent::__construct(
59+
$this->getRenderer()->renderTemplate(
60+
DIRECTORY_SEPARATOR . 'Exception' . DIRECTORY_SEPARATOR . 'InvalidArrayTuplesException.phptpl',
61+
['propertyName' => $propertyName]
62+
),
63+
DIRECTORY_SEPARATOR . 'Validator' . DIRECTORY_SEPARATOR . 'ArrayTuple.phptpl',
64+
[
65+
'tupleProperties' => $tupleProperties,
66+
'viewHelper' => new RenderHelper($schemaProcessor->getGeneratorConfiguration()),
67+
'generatorConfiguration' => $schemaProcessor->getGeneratorConfiguration(),
68+
]
69+
);
70+
}
71+
72+
/**
73+
* Initialize all variables which are required to execute a property names validator
74+
*
75+
* @return string
76+
*/
77+
public function getValidatorSetUp(): string
78+
{
79+
return '$invalidTuples = [];';
80+
}
81+
}

src/Model/Validator/PropertyNamesValidator.php

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ class PropertyNamesValidator extends PropertyTemplateValidator
2727
*
2828
* @param SchemaProcessor $schemaProcessor
2929
* @param Schema $schema
30-
* @param array $propertyNames
30+
* @param array $tuplePropertiesNames
3131
*
3232
* @throws FileSystemException
3333
* @throws SyntaxErrorException
@@ -37,10 +37,10 @@ class PropertyNamesValidator extends PropertyTemplateValidator
3737
public function __construct(
3838
SchemaProcessor $schemaProcessor,
3939
Schema $schema,
40-
array $propertyNames
40+
array $tuplePropertiesNames
4141
) {
4242
$nameValidationProperty = (new StringProcessor(new PropertyCollectionProcessor(), $schemaProcessor, $schema))
43-
->process('property name', $propertyNames)
43+
->process('property name', $tuplePropertiesNames)
4444
// the property name validator doesn't need type checks or required checks so simply filter them out
4545
->filterValidators(function (Validator $validator) {
4646
return !is_a($validator->getValidator(), RequiredPropertyValidator::class) &&

src/ModelGenerator.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,7 @@ public function generateModelDirectory(string $modelPath, int $directoryMode = 0
7272
* @throws FileSystemException Will be thrown if either the $source or the $destination directory doesn't exist
7373
* or the $destination directory is not empty
7474
* @throws SchemaException Will be thrown if a schema is invalid or can't be parsed
75-
* @throws FileSystemException Will be thrown if a file system error occured
75+
* @throws FileSystemException Will be thrown if a file system error occurred
7676
* @throws RenderException Will be thrown if a class can't be rendered correctly
7777
*/
7878
public function generateModels(string $source, string $destination): array

src/PropertyProcessor/Property/ArrayProcessor.php

Lines changed: 48 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66

77
use PHPModelGenerator\Exception\SchemaException;
88
use PHPModelGenerator\Model\Property\PropertyInterface;
9+
use PHPModelGenerator\Model\Validator\ArrayTupleValidator;
910
use PHPModelGenerator\Model\Validator\PropertyTemplateValidator;
1011
use PHPModelGenerator\Model\Validator\PropertyValidator;
1112
use PHPModelGenerator\PropertyProcessor\Decorator\TypeHint\ArrayTypeHintDecorator;
@@ -109,6 +110,16 @@ private function addItemsValidation(PropertyInterface $property, array $property
109110
return;
110111
}
111112

113+
// check if the items require a tuple validation
114+
if (is_array($propertyData[self::JSON_FIELD_ITEMS]) &&
115+
array_keys($propertyData[self::JSON_FIELD_ITEMS]) ===
116+
range(0, count($propertyData[self::JSON_FIELD_ITEMS]) - 1)
117+
) {
118+
$this->addTupleValidator($property, $propertyData);
119+
120+
return;
121+
}
122+
112123
$this->addItemValidator(
113124
$property,
114125
$propertyData[self::JSON_FIELD_ITEMS],
@@ -117,6 +128,43 @@ private function addItemsValidation(PropertyInterface $property, array $property
117128
);
118129
}
119130

131+
/**
132+
* Add the validator to check a tuple validation for each item of the array
133+
*
134+
* @param PropertyInterface $property
135+
* @param array $propertyData
136+
*
137+
* @throws SchemaException
138+
*/
139+
private function addTupleValidator(PropertyInterface $property, array $propertyData): void
140+
{
141+
if (isset($propertyData['additionalItems']) && $propertyData['additionalItems'] !== false) {
142+
// TODO: add validator by reusing the AdditionalPropertiesValidator
143+
}
144+
145+
$tupleCount = count($propertyData[self::JSON_FIELD_ITEMS]);
146+
147+
$property
148+
->addValidator(
149+
new PropertyValidator(
150+
'is_array($value) && count($value) < ' . $tupleCount,
151+
sprintf(
152+
'Missing tuple item in array %s. Requires %s items, got " . count($value) . "',
153+
$property->getName(),
154+
$tupleCount
155+
)
156+
)
157+
)
158+
->addValidator(
159+
new ArrayTupleValidator(
160+
$this->schemaProcessor,
161+
$this->schema,
162+
$propertyData[self::JSON_FIELD_ITEMS],
163+
$property->getName()
164+
)
165+
);
166+
}
167+
120168
/**
121169
* Add the validator to check for constraints required for at least one item
122170
*
@@ -166,7 +214,6 @@ private function addItemValidator(
166214
);
167215

168216
$property
169-
->addNestedProperty($nestedProperty)
170217
->addTypeHintDecorator(new ArrayTypeHintDecorator($nestedProperty))
171218
->addValidator(
172219
new PropertyTemplateValidator(

src/PropertyProcessor/Property/ObjectProcessor.php

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,12 @@ public function process(string $propertyName, array $propertyData): PropertyInte
3030
$propertyData['id'] ?? str_replace(
3131
' ',
3232
'_',
33-
sprintf('%s_%s_%s', $this->schemaProcessor->getCurrentClassName(), $propertyName, uniqid())
33+
sprintf(
34+
'%s_%s_%s',
35+
$this->schemaProcessor->getCurrentClassName(),
36+
preg_replace('/[^a-z0-9\s]/i', '', $propertyName),
37+
uniqid()
38+
)
3439
)
3540
);
3641

src/PropertyProcessor/Property/StringProcessor.php

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,11 @@ protected function addLengthValidator(PropertyInterface $property, array $proper
7070
$property->addValidator(
7171
new PropertyValidator(
7272
$this->getTypeCheck() . "strlen(\$value) < {$propertyData[static::JSON_FIELD_MIN_LENGTH]}",
73-
"{$property->getName()} must not be shorter than {$propertyData[static::JSON_FIELD_MIN_LENGTH]}"
73+
sprintf(
74+
'Value for %s must not be shorter than %s',
75+
$property->getName(),
76+
$propertyData[static::JSON_FIELD_MIN_LENGTH]
77+
)
7478
)
7579
);
7680
}
@@ -79,7 +83,11 @@ protected function addLengthValidator(PropertyInterface $property, array $proper
7983
$property->addValidator(
8084
new PropertyValidator(
8185
$this->getTypeCheck() . "strlen(\$value) > {$propertyData[static::JSON_FIELD_MAX_LENGTH]}",
82-
"{$property->getName()} must not be longer than {$propertyData[static::JSON_FIELD_MAX_LENGTH]}"
86+
sprintf(
87+
'Value for %s must not be longer than %s',
88+
$property->getName(),
89+
$propertyData[static::JSON_FIELD_MAX_LENGTH]
90+
)
8391
)
8492
);
8593
}

0 commit comments

Comments
 (0)