Commit 590ca769 authored by Fabien Potencier's avatar Fabien Potencier

feature #1508 Added WebLink component integration (skalpa)

This PR was merged into the 2.1.x-dev branch.

Discussion
----------

Added WebLink component integration

I made the necessary changes to support the new WebLink component:

- `HttpKernelServiceProvider` registers the `AddLinkHeaderListener` if the component is available
- `TwigServiceProvider` adds the `WebLinkExtension` if the component and the Twig bridge are available
- Both changes are tested
- The documentation has been amended (the link to the Symfony website doesn't work as 3.3 hasn't been released yet but I believe it's the good URL)

Commits
-------

37bd5aed Added WebLink component integration
parents 24ad5c37 37bd5aed
...@@ -47,7 +47,8 @@ ...@@ -47,7 +47,8 @@
"twig/twig": "~1.28|~2.0", "twig/twig": "~1.28|~2.0",
"doctrine/dbal": "~2.2", "doctrine/dbal": "~2.2",
"swiftmailer/swiftmailer": "~5", "swiftmailer/swiftmailer": "~5",
"monolog/monolog": "^1.4.1" "monolog/monolog": "^1.4.1",
"symfony/web-link": "^3.3"
}, },
"replace": { "replace": {
"silex/api": "self.version", "silex/api": "self.version",
......
...@@ -134,6 +134,15 @@ If you are using the ``SecurityServiceProvider``, you will have access to the ...@@ -134,6 +134,15 @@ If you are using the ``SecurityServiceProvider``, you will have access to the
`Symfony Security documentation `Symfony Security documentation
<http://symfony.com/doc/current/book/security.html#access-control-in-templates>`_. <http://symfony.com/doc/current/book/security.html#access-control-in-templates>`_.
Web Link Support
~~~~~~~~~~~~~~~~
If you are using the ``symfony/web-link`` component, you will have access to the
``preload()``, ``prefetch()``, ``prerender()``, ``dns_prefetch()``,
``preconnect()`` and ``link()`` functions in templates. You can find more
information in the `Symfony WebLink documentation
<https://symfony.com/doc/current/components/weblink/introduction.html>`_.
Global Variable Global Variable
~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~
......
...@@ -24,6 +24,8 @@ use Symfony\Component\HttpKernel\ControllerMetadata\ArgumentMetadataFactory; ...@@ -24,6 +24,8 @@ use Symfony\Component\HttpKernel\ControllerMetadata\ArgumentMetadataFactory;
use Symfony\Component\HttpKernel\EventListener\ResponseListener; use Symfony\Component\HttpKernel\EventListener\ResponseListener;
use Symfony\Component\HttpKernel\HttpKernel; use Symfony\Component\HttpKernel\HttpKernel;
use Symfony\Component\HttpKernel\Kernel; use Symfony\Component\HttpKernel\Kernel;
use Symfony\Component\WebLink\EventListener\AddLinkHeaderListener;
use Symfony\Component\WebLink\HttpHeaderSerializer;
class HttpKernelServiceProvider implements ServiceProviderInterface, EventListenerProviderInterface class HttpKernelServiceProvider implements ServiceProviderInterface, EventListenerProviderInterface
{ {
...@@ -91,5 +93,9 @@ class HttpKernelServiceProvider implements ServiceProviderInterface, EventListen ...@@ -91,5 +93,9 @@ class HttpKernelServiceProvider implements ServiceProviderInterface, EventListen
$dispatcher->addSubscriber(new MiddlewareListener($app)); $dispatcher->addSubscriber(new MiddlewareListener($app));
$dispatcher->addSubscriber(new ConverterListener($app['routes'], $app['callback_resolver'])); $dispatcher->addSubscriber(new ConverterListener($app['routes'], $app['callback_resolver']));
$dispatcher->addSubscriber(new StringToResponseListener()); $dispatcher->addSubscriber(new StringToResponseListener());
if (class_exists(HttpHeaderSerializer::class)) {
$dispatcher->addSubscriber(new AddLinkHeaderListener());
}
} }
} }
...@@ -23,9 +23,11 @@ use Symfony\Bridge\Twig\Extension\FormExtension; ...@@ -23,9 +23,11 @@ use Symfony\Bridge\Twig\Extension\FormExtension;
use Symfony\Bridge\Twig\Extension\SecurityExtension; use Symfony\Bridge\Twig\Extension\SecurityExtension;
use Symfony\Bridge\Twig\Extension\HttpFoundationExtension; use Symfony\Bridge\Twig\Extension\HttpFoundationExtension;
use Symfony\Bridge\Twig\Extension\HttpKernelExtension; use Symfony\Bridge\Twig\Extension\HttpKernelExtension;
use Symfony\Bridge\Twig\Extension\WebLinkExtension;
use Symfony\Bridge\Twig\Form\TwigRendererEngine; use Symfony\Bridge\Twig\Form\TwigRendererEngine;
use Symfony\Bridge\Twig\Form\TwigRenderer; use Symfony\Bridge\Twig\Form\TwigRenderer;
use Symfony\Bridge\Twig\Extension\HttpKernelRuntime; use Symfony\Bridge\Twig\Extension\HttpKernelRuntime;
use Symfony\Component\WebLink\HttpHeaderSerializer;
/** /**
* Twig integration for Silex. * Twig integration for Silex.
...@@ -142,6 +144,10 @@ class TwigServiceProvider implements ServiceProviderInterface ...@@ -142,6 +144,10 @@ class TwigServiceProvider implements ServiceProviderInterface
if (class_exists(HttpKernelRuntime::class)) { if (class_exists(HttpKernelRuntime::class)) {
$twig->addRuntimeLoader($app['twig.runtime_loader']); $twig->addRuntimeLoader($app['twig.runtime_loader']);
} }
if (class_exists(HttpHeaderSerializer::class) && class_exists(WebLinkExtension::class)) {
$twig->addExtension(new WebLinkExtension($app['request_stack']));
}
} }
return $twig; return $twig;
......
...@@ -11,6 +11,8 @@ ...@@ -11,6 +11,8 @@
namespace Silex\Tests; namespace Silex\Tests;
use Fig\Link\GenericLinkProvider;
use Fig\Link\Link;
use Silex\Application; use Silex\Application;
use Silex\ControllerCollection; use Silex\ControllerCollection;
use Silex\Api\ControllerProviderInterface; use Silex\Api\ControllerProviderInterface;
...@@ -655,6 +657,22 @@ class ApplicationTest extends \PHPUnit_Framework_TestCase ...@@ -655,6 +657,22 @@ class ApplicationTest extends \PHPUnit_Framework_TestCase
$this->assertEquals('Hello view listener', $response->getContent()); $this->assertEquals('Hello view listener', $response->getContent());
} }
public function testWebLinkListener()
{
$app = new Application();
$app->get('/', function () {
return 'hello';
});
$request = Request::create('/');
$request->attributes->set('_links', (new GenericLinkProvider())->withLink(new Link('preload', '/foo.css')));
$response = $app->handle($request);
$this->assertEquals('</foo.css>; rel="preload"', $response->headers->get('Link'));
}
public function testDefaultRoutesFactory() public function testDefaultRoutesFactory()
{ {
$app = new Application(); $app = new Application();
......
...@@ -11,11 +11,13 @@ ...@@ -11,11 +11,13 @@
namespace Silex\Tests\Provider; namespace Silex\Tests\Provider;
use Fig\Link\Link;
use Silex\Application; use Silex\Application;
use Silex\Provider\CsrfServiceProvider; use Silex\Provider\CsrfServiceProvider;
use Silex\Provider\FormServiceProvider; use Silex\Provider\FormServiceProvider;
use Silex\Provider\TwigServiceProvider; use Silex\Provider\TwigServiceProvider;
use Silex\Provider\AssetServiceProvider; use Silex\Provider\AssetServiceProvider;
use Symfony\Bridge\Twig\Extension\WebLinkExtension;
use Symfony\Component\HttpFoundation\Request; use Symfony\Component\HttpFoundation\Request;
/** /**
...@@ -138,4 +140,24 @@ class TwigServiceProviderTest extends \PHPUnit_Framework_TestCase ...@@ -138,4 +140,24 @@ class TwigServiceProviderTest extends \PHPUnit_Framework_TestCase
$this->assertSame($timezone, $twig->getExtension('Twig_Extension_Core')->getTimezone()); $this->assertSame($timezone, $twig->getExtension('Twig_Extension_Core')->getTimezone());
$this->assertSame(array(2, ',', ' '), $twig->getExtension('Twig_Extension_Core')->getNumberFormat()); $this->assertSame(array(2, ',', ' '), $twig->getExtension('Twig_Extension_Core')->getNumberFormat());
} }
public function testWebLinkIntegration()
{
if (!class_exists(WebLinkExtension::class)) {
$this->markTestSkipped('Twig WebLink extension not available.');
}
$app = new Application();
$app['request_stack']->push($request = Request::create('/'));
$app->register(new TwigServiceProvider(), array(
'twig.templates' => array(
'preload' => '{{ preload("/foo.css") }}',
),
));
$this->assertEquals('/foo.css', $app['twig']->render('preload'));
$link = new Link('preload', '/foo.css');
$this->assertEquals(array($link), array_values($request->attributes->get('_links')->getLinks()));
}
} }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment