diff --git a/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Configuration.php b/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Configuration.php index 0c1d1578c6f0..b79bea6ad0ad 100644 --- a/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Configuration.php +++ b/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Configuration.php @@ -85,6 +85,7 @@ public function getConfigTreeBuilder() $this->addProfilerSection($rootNode); $this->addRouterSection($rootNode); $this->addSessionSection($rootNode); + $this->addRequestSection($rootNode); $this->addTemplatingSection($rootNode); $this->addTranslatorSection($rootNode); $this->addValidationSection($rootNode); @@ -256,6 +257,35 @@ private function addSessionSection(ArrayNodeDefinition $rootNode) ; } + private function addRequestSection(ArrayNodeDefinition $rootNode) + { + $rootNode + ->children() + ->arrayNode('request') + ->info('request configuration') + ->canBeUnset() + ->fixXmlConfig('format') + ->children() + ->arrayNode('formats') + ->useAttributeAsKey('name') + ->prototype('array') + ->beforeNormalization() + ->ifTrue(function ($v) { return is_array($v) && isset($v['mime_type']); }) + ->then(function ($v) { return $v['mime_type']; }) + ->end() + ->beforeNormalization() + ->ifTrue(function ($v) { return !is_array($v); }) + ->then(function ($v) { return array($v); }) + ->end() + ->prototype('scalar')->end() + ->end() + ->end() + ->end() + ->end() + ->end() + ; + } + private function addTemplatingSection(ArrayNodeDefinition $rootNode) { $organizeUrls = function ($urls) { diff --git a/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php b/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php index 5dc5c05513f0..3221e74d92d1 100644 --- a/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php +++ b/src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php @@ -91,6 +91,10 @@ public function load(array $configs, ContainerBuilder $container) $this->registerSessionConfiguration($config['session'], $container, $loader); } + if (isset($config['request'])) { + $this->registerRequestConfiguration($config['request'], $container, $loader); + } + $loader->load('security.xml'); if ($this->isConfigEnabled($container, $config['form'])) { @@ -382,6 +386,24 @@ private function registerSessionConfiguration(array $config, ContainerBuilder $c $container->setParameter('session.metadata.update_threshold', $config['metadata_update_threshold']); } + /** + * Loads the request configuration. + * + * @param array $config A session configuration array + * @param ContainerBuilder $container A ContainerBuilder instance + * @param XmlFileLoader $loader An XmlFileLoader instance + */ + private function registerRequestConfiguration(array $config, ContainerBuilder $container, XmlFileLoader $loader) + { + if ($config['formats']) { + $loader->load('request.xml'); + $container + ->getDefinition('request.add_request_formats_listener') + ->replaceArgument(0, $config['formats']) + ; + } + } + /** * Loads the templating configuration. * diff --git a/src/Symfony/Bundle/FrameworkBundle/Resources/config/request.xml b/src/Symfony/Bundle/FrameworkBundle/Resources/config/request.xml new file mode 100644 index 000000000000..cc836c35e3b0 --- /dev/null +++ b/src/Symfony/Bundle/FrameworkBundle/Resources/config/request.xml @@ -0,0 +1,17 @@ + + + + + + Symfony\Component\HttpKernel\EventListener\AddRequestFormatsListener + + + + + + + + + diff --git a/src/Symfony/Bundle/FrameworkBundle/Resources/config/schema/symfony-1.0.xsd b/src/Symfony/Bundle/FrameworkBundle/Resources/config/schema/symfony-1.0.xsd index 92c8952e48be..fcc9e254589d 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Resources/config/schema/symfony-1.0.xsd +++ b/src/Symfony/Bundle/FrameworkBundle/Resources/config/schema/symfony-1.0.xsd @@ -16,6 +16,7 @@ + @@ -101,6 +102,19 @@ + + + + + + + + + + + + + diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/php/full.php b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/php/full.php index c4eff9349228..8bdb59f33d73 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/php/full.php +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/php/full.php @@ -70,5 +70,14 @@ 'debug' => true, 'file_cache_dir' => '%kernel.cache_dir%/annotations', ), - 'ide' => 'file%%link%%format' + 'ide' => 'file%%link%%format', + 'request' => array( + 'formats' => array( + 'csv' => array( + 'text/csv', + 'text/plain', + ), + 'pdf' => 'application/pdf' + ) + ) )); diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/php/request.php b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/php/request.php new file mode 100644 index 000000000000..1e7cb2921c4c --- /dev/null +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/php/request.php @@ -0,0 +1,7 @@ +loadFromExtension('framework', array( + 'request' => array( + 'formats' => array(), + ), +)); diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/xml/full.xml b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/xml/full.xml index 8fd3e9b6528a..da3a5355467b 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/xml/full.xml +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/xml/full.xml @@ -13,6 +13,15 @@ + + + text/csv + text/plain + + + application/pdf + + loader.foo loader.bar diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/xml/request.xml b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/xml/request.xml new file mode 100644 index 000000000000..320d1b187525 --- /dev/null +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/xml/request.xml @@ -0,0 +1,11 @@ + + + + + + + diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/yml/full.yml b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/yml/full.yml index d013063916c3..2e6f4c5388d1 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/yml/full.yml +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/yml/full.yml @@ -55,3 +55,7 @@ framework: debug: true file_cache_dir: %kernel.cache_dir%/annotations ide: file%%link%%format + request: + formats: + csv: ['text/csv', 'text/plain'] + pdf: 'application/pdf' diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/yml/request.yml b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/yml/request.yml new file mode 100644 index 000000000000..9beae1dc5975 --- /dev/null +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/yml/request.yml @@ -0,0 +1,3 @@ +framework: + request: + formats: ~ diff --git a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/FrameworkExtensionTest.php b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/FrameworkExtensionTest.php index 94ba71d44857..d36203e3682d 100644 --- a/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/FrameworkExtensionTest.php +++ b/src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/FrameworkExtensionTest.php @@ -145,6 +145,22 @@ public function testNullSessionHandler() $this->assertNull($container->getDefinition('session.storage.php_bridge')->getArgument(0)); } + public function testRequest() + { + $container = $this->createContainerFromFile('full'); + + $this->assertTrue($container->hasDefinition('request.add_request_formats_listener'), '->registerRequestConfiguration() loads request.xml'); + $listenerDef = $container->getDefinition('request.add_request_formats_listener'); + $this->assertEquals(array('csv' => array('text/csv', 'text/plain'), 'pdf' => array('application/pdf')), $listenerDef->getArgument(0)); + } + + public function testEmptyRequestFormats() + { + $container = $this->createContainerFromFile('request'); + + $this->assertFalse($container->hasDefinition('request.add_request_formats_listener'), '->registerRequestConfiguration() does not load request.xml when no request formats are defined'); + } + public function testTemplating() { $container = $this->createContainerFromFile('full'); diff --git a/src/Symfony/Component/HttpKernel/EventListener/AddRequestFormatsListener.php b/src/Symfony/Component/HttpKernel/EventListener/AddRequestFormatsListener.php new file mode 100644 index 000000000000..c37a537009e9 --- /dev/null +++ b/src/Symfony/Component/HttpKernel/EventListener/AddRequestFormatsListener.php @@ -0,0 +1,57 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\HttpKernel\EventListener; + +use Symfony\Component\EventDispatcher\EventSubscriberInterface; +use Symfony\Component\HttpKernel\KernelEvents; +use Symfony\Component\HttpKernel\Event\GetResponseEvent; + +/** + * Adds configured formats to each request + * + * @author Gildas Quemener + */ +class AddRequestFormatsListener implements EventSubscriberInterface +{ + /** + * @var array + */ + protected $formats; + + /** + * @param array $formats + */ + public function __construct(array $formats) + { + $this->formats = $formats; + } + + /** + * Adds request formats + * + * @param GetResponseEvent $event + */ + public function onKernelRequest(GetResponseEvent $event) + { + foreach ($this->formats as $format => $mimeTypes) { + $event->getRequest()->setFormat($format, $mimeTypes); + } + } + + /** + * {@inheritdoc} + */ + public static function getSubscribedEvents() + { + return array(KernelEvents::REQUEST => 'onKernelRequest'); + } +} diff --git a/src/Symfony/Component/HttpKernel/Tests/EventListener/AddRequestFormatsListenerTest.php b/src/Symfony/Component/HttpKernel/Tests/EventListener/AddRequestFormatsListenerTest.php new file mode 100644 index 000000000000..26bdf7067374 --- /dev/null +++ b/src/Symfony/Component/HttpKernel/Tests/EventListener/AddRequestFormatsListenerTest.php @@ -0,0 +1,83 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\HttpKernel\Tests\EventListener; + +use Symfony\Component\HttpKernel\EventListener\AddRequestFormatsListener; +use Symfony\Component\HttpFoundation\Request; +use Symfony\Component\HttpKernel\KernelEvents; + +/** + * Test AddRequestFormatsListener class + * + * @author Gildas Quemener + */ +class AddRequestFormatsListenerTest extends \PHPUnit_Framework_TestCase +{ + /** + * @var AddRequestFormatsListener + */ + private $listener; + + protected function setUp() + { + $this->listener = new AddRequestFormatsListener(array('csv' => array('text/csv', 'text/plain'))); + } + + protected function tearDown() + { + $this->listener = null; + } + + public function testIsAnEventSubscriber() + { + $this->assertInstanceOf('Symfony\Component\EventDispatcher\EventSubscriberInterface', $this->listener); + } + + public function testRegisteredEvent() + { + $this->assertEquals( + array(KernelEvents::REQUEST => 'onKernelRequest'), + AddRequestFormatsListener::getSubscribedEvents() + ); + } + + public function testSetAdditionalFormats() + { + $request = $this->getRequestMock(); + $event = $this->getGetResponseEventMock($request); + + $request->expects($this->once()) + ->method('setFormat') + ->with('csv', array('text/csv', 'text/plain')); + + $this->listener->onKernelRequest($event); + } + + protected function getRequestMock() + { + return $this->getMock('Symfony\Component\HttpFoundation\Request'); + } + + protected function getGetResponseEventMock(Request $request) + { + $event = $this + ->getMockBuilder('Symfony\Component\HttpKernel\Event\GetResponseEvent') + ->disableOriginalConstructor() + ->getMock(); + + $event->expects($this->any()) + ->method('getRequest') + ->will($this->returnValue($request)); + + return $event; + } +}