Fix support without twig (#1878)

* fix support without twig

* Support null openApiRenderer

* Register a twig extension instead of registering twig function at runtime

* fix tests
This commit is contained in:
Guilhem Niot 2021-09-22 23:43:32 +02:00 committed by GitHub
parent b53edda10c
commit 9c729ab7b7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 33 additions and 26 deletions

View File

@ -155,6 +155,9 @@ final class NelmioApiDocExtension extends Extension implements PrependExtensionI
$bundles = $container->getParameter('kernel.bundles');
if (!isset($bundles['TwigBundle'])) {
$container->removeDefinition('nelmio_api_doc.controller.swagger_ui');
$container->removeDefinition('nelmio_api_doc.render_docs.html');
$container->removeDefinition('nelmio_api_doc.render_docs.html.asset');
}
if (isset($bundles['ApiPlatformBundle']) && class_exists('ApiPlatform\Core\Documentation\Documentation')) {
$loader->load('api_platform.xml');

View File

@ -12,17 +12,17 @@
namespace Nelmio\ApiDocBundle\Render\Html;
use Symfony\Bridge\Twig\Extension\AssetExtension;
use Twig\Extension\AbstractExtension;
use Twig\TwigFunction;
/**
* @internal
*/
class GetNelmioAsset
class GetNelmioAsset extends AbstractExtension
{
private $assetExtension;
private $resourcesDir;
private $cdnUrl;
private $assetsMode = AssetsMode::BUNDLE;
public function __construct(AssetExtension $assetExtension)
{
@ -31,16 +31,16 @@ class GetNelmioAsset
$this->resourcesDir = __DIR__.'/../../Resources/public';
}
public function toTwigFunction($assetsMode): TwigFunction
public function getFunctions()
{
$this->assetsMode = $assetsMode;
return new TwigFunction('nelmioAsset', $this, ['is_safe' => ['html']]);
return [
new TwigFunction('nelmioAsset', $this, ['is_safe' => ['html']]),
];
}
public function __invoke($asset)
public function __invoke($defaultAssetsMode, $asset)
{
[$extension, $mode] = $this->getExtension($asset);
[$extension, $mode] = $this->getExtension($defaultAssetsMode, $asset);
[$resource, $isInline] = $this->getResource($asset, $mode);
if ('js' == $extension) {
return $this->renderJavascript($resource, $isInline);
@ -51,15 +51,15 @@ class GetNelmioAsset
}
}
private function getExtension($asset)
private function getExtension($assetsMode, $asset)
{
$extension = mb_substr($asset, -3, 3, 'utf-8');
if ('.js' === $extension) {
return ['js', $this->assetsMode];
return ['js', $assetsMode];
} elseif ('png' === $extension) {
return ['png', AssetsMode::OFFLINE == $this->assetsMode ? AssetsMode::CDN : $this->assetsMode];
return ['png', AssetsMode::OFFLINE == $assetsMode ? AssetsMode::CDN : $assetsMode];
} else {
return ['css', $this->assetsMode];
return ['css', $assetsMode];
}
}

View File

@ -28,13 +28,12 @@ class HtmlOpenApiRenderer implements OpenApiRenderer
/** @var GetNelmioAsset */
private $getNelmioAsset;
public function __construct($twig, GetNelmioAsset $getNelmioAsset)
public function __construct($twig)
{
if (!$twig instanceof \Twig_Environment && !$twig instanceof Environment) {
throw new InvalidArgumentException(sprintf('Providing an instance of "%s" as twig is not supported.', get_class($twig)));
}
$this->twig = $twig;
$this->getNelmioAsset = $getNelmioAsset;
}
public function getFormat(): string
@ -49,8 +48,6 @@ class HtmlOpenApiRenderer implements OpenApiRenderer
'swagger_ui_config' => [],
];
$this->twig->addFunction($this->getNelmioAsset->toTwigFunction($options['assets_mode']));
return $this->twig->render(
'@NelmioApiDoc/SwaggerUi/index.html.twig',
[

View File

@ -33,6 +33,10 @@ class RenderOpenApi
{
$this->generatorLocator = $generatorLocator;
foreach ($openApiRenderers as $openApiRenderer) {
if (null === $openApiRenderer) {
continue;
}
$this->openApiRenderers[$openApiRenderer->getFormat()] = $openApiRenderer;
}
}

View File

@ -28,16 +28,17 @@
<!-- Render -->
<service id="nelmio_api_doc.render_docs" class="Nelmio\ApiDocBundle\Render\RenderOpenApi" public="true">
<argument type="service" id="nelmio_api_doc.generator_locator" />
<argument type="service" id="nelmio_api_doc.render_docs.html" />
<argument type="service" id="nelmio_api_doc.render_docs.json" />
<argument type="service" id="nelmio_api_doc.render_docs.yaml" />
<argument type="service" id="nelmio_api_doc.render_docs.html" on-invalid="ignore" />
</service>
<service id="nelmio_api_doc.render_docs.html" class="Nelmio\ApiDocBundle\Render\Html\HtmlOpenApiRenderer" public="false">
<argument type="service" id="twig" />
<argument type="service" id="nelmio_api_doc.render_docs.html.asset" />
</service>
<service id="nelmio_api_doc.render_docs.html.asset" class="Nelmio\ApiDocBundle\Render\Html\GetNelmioAsset" public="false">
<argument type="service" id="twig.extension.assets" />
<tag name="twig.extension" />
</service>
<service id="nelmio_api_doc.render_docs.json" class="Nelmio\ApiDocBundle\Render\Json\JsonOpenApiRenderer" public="false">
</service>

View File

@ -14,8 +14,8 @@ file that was distributed with this source code. #}
<title>{% block title %}{{ swagger_data.spec.info.title }}{% endblock title %}</title>
{% block stylesheets %}
{{ nelmioAsset('swagger-ui/swagger-ui.css') }}
{{ nelmioAsset('style.css') }}
{{ nelmioAsset(assets_mode, 'swagger-ui/swagger-ui.css') }}
{{ nelmioAsset(assets_mode, 'style.css') }}
{% endblock stylesheets %}
{% block swagger_data %}
@ -54,7 +54,7 @@ file that was distributed with this source code. #}
<header>
{% block header %}
<a id="logo" href="https://github.com/nelmio/NelmioApiDocBundle">
<img src="{{ nelmioAsset('logo.png') }}" alt="NelmioApiDocBundle">
<img src="{{ nelmioAsset(assets_mode, 'logo.png') }}" alt="NelmioApiDocBundle">
</a>
{% endblock header %}
</header>
@ -64,11 +64,11 @@ file that was distributed with this source code. #}
{% endblock %}
{% block javascripts %}
{{ nelmioAsset('swagger-ui/swagger-ui-bundle.js') }}
{{ nelmioAsset('swagger-ui/swagger-ui-standalone-preset.js') }}
{{ nelmioAsset(assets_mode, 'swagger-ui/swagger-ui-bundle.js') }}
{{ nelmioAsset(assets_mode, 'swagger-ui/swagger-ui-standalone-preset.js') }}
{% endblock javascripts %}
{{ nelmioAsset('init-swagger-ui.js') }}
{{ nelmioAsset(assets_mode, 'init-swagger-ui.js') }}
{% block swagger_initialization %}
<script type="text/javascript">

View File

@ -14,6 +14,7 @@ namespace Nelmio\ApiDocBundle\Tests\Render\Html;
use Nelmio\ApiDocBundle\Render\Html\AssetsMode;
use Nelmio\ApiDocBundle\Render\Html\GetNelmioAsset;
use Nelmio\ApiDocBundle\Tests\Functional\WebTestCase;
use Twig\TwigFunction;
class GetNelmioAssetTest extends WebTestCase
{
@ -23,8 +24,9 @@ class GetNelmioAssetTest extends WebTestCase
static::bootKernel();
/** @var GetNelmioAsset $getNelmioAsset */
$getNelmioAsset = static::$container->get('nelmio_api_doc.render_docs.html.asset');
$twigFunction = $getNelmioAsset->toTwigFunction($mode);
self::assertSame($expectedContent, $twigFunction->getCallable()->__invoke($asset, $mode));
/** @var TwigFunction */
$twigFunction = $getNelmioAsset->getFunctions()[0];
self::assertSame($expectedContent, $twigFunction->getCallable()->__invoke($mode, $asset));
}
public function provideAsset()