mirror of
https://github.com/retailcrm/NelmioApiDocBundle.git
synced 2025-03-12 02:26:09 +03:00
Added describer that removes duplicate parameters when using $ref.
This commit is contained in:
parent
9ab9d6da72
commit
9b9dbe69dd
79
Describer/ParameterRefMergeDescriber.php
Normal file
79
Describer/ParameterRefMergeDescriber.php
Normal file
@ -0,0 +1,79 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of the NelmioApiDocBundle package.
|
||||
*
|
||||
* (c) Nelmio
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
|
||||
namespace Nelmio\ApiDocBundle\Describer;
|
||||
|
||||
use EXSyst\Component\Swagger\Collections\Parameters;
|
||||
use EXSyst\Component\Swagger\Operation;
|
||||
use EXSyst\Component\Swagger\Parameter;
|
||||
use EXSyst\Component\Swagger\Path;
|
||||
use EXSyst\Component\Swagger\Swagger;
|
||||
|
||||
/**
|
||||
* Merges parameters that have been added as refs through config files with those that get auto generated based on
|
||||
* routes.
|
||||
*/
|
||||
class ParameterRefMergeDescriber implements DescriberInterface
|
||||
{
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function describe(Swagger $api)
|
||||
{
|
||||
/** @var Path $path */
|
||||
foreach ($api->getPaths() as $path) {
|
||||
/** @var Operation $operation */
|
||||
foreach ($path->getOperations() as $operation) {
|
||||
$this->checkOperation($api, $operation);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* This method removes parameters that also have a ref version as they will be duplicated otherwise.
|
||||
*/
|
||||
private function checkOperation(Swagger $api, Operation $operation)
|
||||
{
|
||||
$parametersToRemove = [];
|
||||
|
||||
/** @var Parameter[] $globalParams */
|
||||
$globalParams = $api->getParameters();
|
||||
/** @var Parameters|Parameter[] $currentParams */
|
||||
$currentParams = $operation->getParameters();
|
||||
|
||||
foreach ($currentParams as $parameter) {
|
||||
$ref = $parameter->getRef();
|
||||
|
||||
if (null === $ref) {
|
||||
// we only concern ourselves with '$ref' parameters
|
||||
continue;
|
||||
}
|
||||
|
||||
$ref = \mb_substr($ref, 13); // trim the '#/parameters/' part of ref
|
||||
if (!isset($globalParams[$ref])) {
|
||||
// this really shouldn't happen, if it does there will be other failures elsewhere, so just ignore here
|
||||
continue;
|
||||
}
|
||||
|
||||
$refParameter = $globalParams[$ref];
|
||||
// param ids are in form {name}/{in}
|
||||
$refParameterId = \sprintf('%s/%s', $refParameter->getName(), $refParameter->getIn());
|
||||
if ($currentParams->has($refParameterId)) {
|
||||
// if we got here it means a duplicate parameter is directly defined, schedule it for removal
|
||||
$parametersToRemove[] = $currentParams->get($refParameterId);
|
||||
}
|
||||
}
|
||||
|
||||
foreach ($parametersToRemove as $parameterToRemove) {
|
||||
$currentParams->remove($parameterToRemove);
|
||||
}
|
||||
}
|
||||
}
|
@ -32,6 +32,10 @@
|
||||
<tag name="nelmio_api_doc.describer" priority="-1000" />
|
||||
</service>
|
||||
|
||||
<service id="nelmio_api_doc.describers.param_ref_merge" class="Nelmio\ApiDocBundle\Describer\ParameterRefMergeDescriber" public="false">
|
||||
<tag name="nelmio_api_doc.describer" priority="-999" />
|
||||
</service>
|
||||
|
||||
<!-- Routing Describers -->
|
||||
<service id="nelmio_api_doc.route_describers.route_metadata" class="Nelmio\ApiDocBundle\RouteDescriber\RouteMetadataDescriber" public="false">
|
||||
<tag name="nelmio_api_doc.route_describer" priority="-300" />
|
||||
|
@ -12,10 +12,12 @@
|
||||
namespace Nelmio\ApiDocBundle\Tests\Describer;
|
||||
|
||||
use EXSyst\Component\Swagger\Swagger;
|
||||
use Nelmio\ApiDocBundle\Describer\DescriberInterface;
|
||||
use PHPUnit\Framework\TestCase;
|
||||
|
||||
abstract class AbstractDescriberTest extends TestCase
|
||||
{
|
||||
/** @var DescriberInterface */
|
||||
protected $describer;
|
||||
|
||||
protected function getSwaggerDoc(): Swagger
|
||||
|
64
Tests/Describer/ParameterRefMergeDescriberTest.php
Normal file
64
Tests/Describer/ParameterRefMergeDescriberTest.php
Normal file
@ -0,0 +1,64 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of the NelmioApiDocBundle package.
|
||||
*
|
||||
* (c) Nelmio
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
|
||||
namespace Nelmio\ApiDocBundle\Tests\Describer;
|
||||
|
||||
use EXSyst\Component\Swagger\Swagger;
|
||||
use Nelmio\ApiDocBundle\Describer\ParameterRefMergeDescriber;
|
||||
|
||||
class ParameterRefMergeDescriberTest extends AbstractDescriberTest
|
||||
{
|
||||
public function testDescribe()
|
||||
{
|
||||
// this sample config was taken from a json generated by swagger without ParameterRefMergeDescriber
|
||||
$apiDef = [
|
||||
'swagger' => '2.0',
|
||||
'info' => ['title' => 'Ref Test'],
|
||||
'paths' => [
|
||||
'/api/{version}/product' => [
|
||||
'get' => [
|
||||
'parameters' => [
|
||||
[
|
||||
'$ref' => '#/parameters/versionParam',
|
||||
],
|
||||
[
|
||||
'name' => 'version',
|
||||
'in' => 'path',
|
||||
'required' => true,
|
||||
'type' => 'string',
|
||||
'pattern' => 'v\\d+',
|
||||
],
|
||||
],
|
||||
],
|
||||
],
|
||||
],
|
||||
'parameters' => [
|
||||
'versionParam' => [
|
||||
'name' => 'version',
|
||||
'in' => 'path',
|
||||
'required' => true,
|
||||
'type' => 'string',
|
||||
],
|
||||
],
|
||||
];
|
||||
$api = new Swagger($apiDef);
|
||||
$this->describer->describe($api);
|
||||
|
||||
$describedData = $api->toArray();
|
||||
// only one parameter should remain as they were duplicates
|
||||
$this->assertCount(1, $describedData['paths']['/api/{version}/product']['get']['parameters']);
|
||||
}
|
||||
|
||||
protected function setUp()
|
||||
{
|
||||
$this->describer = new ParameterRefMergeDescriber();
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user