Skip to content
Prev Previous commit
Next Next commit
[Slim4] Add mockFromRef method
  • Loading branch information
ybelenko committed Jan 8, 2020
commit cba5c340790f0c6dc97dd85614ee868b4bdd1adc
Original file line number Diff line number Diff line change
Expand Up @@ -284,21 +284,8 @@ final class OpenApiDataMocker implements IMocker
// always generate smallest possible array to avoid huge JSON responses
$arrSize = ($maxSize < 1) ? $maxSize : max($minSize, 1);
while (count($arr) < $arrSize) {
if (is_string($ref) && !empty($ref)) {
$refName = static::getSimpleRef($ref);
$modelName = static::toModelName($refName);
$modelClass = '{{modelPackage}}\\' . $modelName;
if (!class_exists($modelClass) || !method_exists($modelClass, 'getOpenApiSchema')) {
throw new InvalidArgumentException(sprintf(
'Model %s not found or method %s doesn\'t exist',
$modelClass,
$modelClass . '::getOpenApiSchema'
));
}
$arr[] = $this->mockFromSchema($modelClass::getOpenApiSchema());
} else {
$arr[] = $this->mock($dataType, $dataFormat, $options);
}
$data = $this->mockFromRef($ref);
$arr[] = ($data) ? $data : $this->mock($dataType, $dataFormat, $options);
}
return $arr;
}
Expand Down Expand Up @@ -402,6 +389,34 @@ final class OpenApiDataMocker implements IMocker
return $this->mock($props['type'], $props['format'], $props);
}

/**
* Mock data by referenced schema.
* TODO: this method will return model instance, not an StdClass
*
* @param string|null $ref Ref to model, eg. #/components/schemas/User
*
* @return mixed
*/
public function mockFromRef($ref)
{
$data = null;
if (is_string($ref) && !empty($ref)) {
$refName = static::getSimpleRef($ref);
$modelName = static::toModelName($refName);
$modelClass = '{{modelPackage}}\\' . $modelName;
if (!class_exists($modelClass) || !method_exists($modelClass, 'getOpenApiSchema')) {
throw new InvalidArgumentException(sprintf(
'Model %s not found or method %s doesn\'t exist',
$modelClass,
$modelClass . '::getOpenApiSchema'
));
}
$data = $this->mockFromSchema($modelClass::getOpenApiSchema(true));
}

return $data;
}

/**
* @internal Extract OAS properties from array or object.
* @codeCoverageIgnore
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -248,5 +248,17 @@ interface {{interfaceNamePrefix}}OpenApiDataMocker{{interfaceNameSuffix}}
* @return mixed
*/
public function mockFromSchema($schema);

/**
* Mock data by referenced schema.
* TODO: this method will return model instance, not an StdClass
*
* @param string|null $ref Ref to model, eg. #/components/schemas/User
*
* @throws \InvalidArgumentException when invalid arguments passed
*
* @return mixed
*/
public function mockFromRef($ref);
}
{{/apiInfo}}
Original file line number Diff line number Diff line change
Expand Up @@ -658,23 +658,38 @@ class OpenApiDataMockerTest extends TestCase
}

/**
* @dataProvider provideMockArrayWithRefArguments
* @covers ::mockArray
*/
public function testMockArrayWithRef()
public function testMockArrayWithRef($items, $expectedStructure)
{
$mocker = new OpenApiDataMocker();
$arr = $mocker->mockArray(['$ref' => '#/components/schemas/CatRefTestClass']);
$arr = $mocker->mockArray($items);
$this->assertIsArray($arr);
$this->assertCount(1, $arr);
foreach ($arr as $item) {
// TODO: replace with assertInstanceOf assertion
$this->assertInternalType(IsType::TYPE_OBJECT, $item);
$this->assertInternalType(IsType::TYPE_STRING, $item->className);
$this->assertInternalType(IsType::TYPE_STRING, $item->color);
$this->assertInternalType(IsType::TYPE_BOOL, $item->declawed);
foreach ($expectedStructure as $expectedProp => $expectedType) {
$this->assertInternalType($expectedType, $item->$expectedProp);
}
}
}

public function provideMockArrayWithRefArguments()
{
return [
'items with ref to CatRefTestClass' => [
['$ref' => '#/components/schemas/CatRefTestClass'],
[
'className' => IsType::TYPE_STRING,
'color' => IsType::TYPE_STRING,
'declawed' => IsType::TYPE_BOOL,
],
],
];
}

/**
* @dataProvider provideMockObjectCorrectArguments
* @covers ::mockObject
Expand Down Expand Up @@ -906,6 +921,52 @@ class OpenApiDataMockerTest extends TestCase
'DateTime object' => [new DateTime()],
];
}

/**
* @dataProvider provideMockFromRefCorrectArguments
* @covers ::mockFromRef
*/
public function testMockFromRefWithCorrectArguments($ref, $expectedStructure)
{
$mocker = new OpenApiDataMocker();
$data = $mocker->mockFromRef($ref);
foreach ($expectedStructure as $expectedProp => $expectedType) {
$this->assertInternalType($expectedType, $data->$expectedProp);
}
}

public function provideMockFromRefCorrectArguments()
{
return [
'CatRefTestClass model' => [
'#/components/schemas/CatRefTestClass',
[
'className' => IsType::TYPE_STRING,
'color' => IsType::TYPE_STRING,
'declawed' => IsType::TYPE_BOOL,
]
],
];
}

/**
* @dataProvider provideMockFromRefInvalidArguments
* @expectedException \InvalidArgumentException
* @covers ::mockFromRef
*/
public function testMockFromRefWithInvalidArguments($ref)
{
$mocker = new OpenApiDataMocker();
$data = $mocker->mockFromRef($ref);
}

public function provideMockFromRefInvalidArguments()
{
return [
'ref to unknown class' => ['#/components/schemas/UnknownClass'],
'ref to class without getOpenApiSchema method' => ['#/components/schemas/ClassWithoutGetSchemaMethod'],
];
}
}

namespace {{modelPackage}};
Expand Down