4 * This file is part of the Symfony package.
6 * (c) Fabien Potencier <fabien@symfony.com>
8 * For the full copyright and license information, please view the LICENSE
9 * file that was distributed with this source code.
12 namespace Symfony\Component\HttpKernel\Tests\EventListener;
14 use PHPUnit\Framework\TestCase;
15 use Symfony\Component\DependencyInjection\ServiceSubscriberInterface;
16 use Symfony\Component\HttpFoundation\Request;
17 use Symfony\Component\HttpFoundation\Response;
18 use Symfony\Component\HttpFoundation\Session\SessionInterface;
19 use Symfony\Component\HttpKernel\Event\FilterResponseEvent;
20 use Symfony\Component\HttpKernel\Event\GetResponseEvent;
21 use Symfony\Component\HttpKernel\EventListener\SessionListener;
22 use Symfony\Component\HttpKernel\EventListener\TestSessionListener;
23 use Symfony\Component\HttpKernel\HttpKernelInterface;
26 * SessionListenerTest.
28 * Tests SessionListener.
30 * @author Bulat Shakirzyanov <mallluhuct@gmail.com>
32 class TestSessionListenerTest extends TestCase
35 * @var TestSessionListener
40 * @var SessionInterface
44 protected function setUp()
46 $this->listener = $this->getMockForAbstractClass('Symfony\Component\HttpKernel\EventListener\AbstractTestSessionListener');
47 $this->session = $this->getSession();
48 $this->listener->expects($this->any())
49 ->method('getSession')
50 ->will($this->returnValue($this->session));
53 public function testShouldSaveMasterRequestSession()
55 $this->sessionHasBeenStarted();
56 $this->sessionMustBeSaved();
58 $this->filterResponse(new Request());
61 public function testShouldNotSaveSubRequestSession()
63 $this->sessionMustNotBeSaved();
65 $this->filterResponse(new Request(), HttpKernelInterface::SUB_REQUEST);
68 public function testDoesNotDeleteCookieIfUsingSessionLifetime()
70 $this->sessionHasBeenStarted();
72 @ini_set('session.cookie_lifetime', 0);
74 $response = $this->filterResponse(new Request(), HttpKernelInterface::MASTER_REQUEST);
75 $cookies = $response->headers->getCookies();
77 $this->assertEquals(0, reset($cookies)->getExpiresTime());
81 * @requires function \Symfony\Component\HttpFoundation\Session\Session::isEmpty
83 public function testEmptySessionDoesNotSendCookie()
85 $this->sessionHasBeenStarted();
86 $this->sessionIsEmpty();
88 $response = $this->filterResponse(new Request(), HttpKernelInterface::MASTER_REQUEST);
90 $this->assertSame(array(), $response->headers->getCookies());
93 public function testEmptySessionWithNewSessionIdDoesSendCookie()
95 $this->sessionHasBeenStarted();
96 $this->sessionIsEmpty();
97 $this->fixSessionId('456');
99 $kernel = $this->getMockBuilder('Symfony\Component\HttpKernel\HttpKernelInterface')->getMock();
100 $request = Request::create('/', 'GET', array(), array('MOCKSESSID' => '123'));
101 $event = new GetResponseEvent($kernel, $request, HttpKernelInterface::MASTER_REQUEST);
102 $this->listener->onKernelRequest($event);
104 $response = $this->filterResponse(new Request(), HttpKernelInterface::MASTER_REQUEST);
106 $this->assertNotEmpty($response->headers->getCookies());
110 * @dataProvider anotherCookieProvider
112 public function testSessionWithNewSessionIdAndNewCookieDoesNotSendAnotherCookie($existing, array $expected)
114 $this->sessionHasBeenStarted();
115 $this->sessionIsEmpty();
116 $this->fixSessionId('456');
118 $kernel = $this->getMockBuilder('Symfony\Component\HttpKernel\HttpKernelInterface')->getMock();
119 $request = Request::create('/', 'GET', array(), array('MOCKSESSID' => '123'));
120 $event = new GetResponseEvent($kernel, $request, HttpKernelInterface::MASTER_REQUEST);
121 $this->listener->onKernelRequest($event);
123 $response = new Response('', 200, array('Set-Cookie' => $existing));
125 $response = $this->filterResponse(new Request(), HttpKernelInterface::MASTER_REQUEST, $response);
127 $this->assertSame($expected, $response->headers->get('Set-Cookie', null, false));
130 public function anotherCookieProvider()
133 'same' => array('MOCKSESSID=789; path=/', array('MOCKSESSID=789; path=/')),
134 'different domain' => array('MOCKSESSID=789; path=/; domain=example.com', array('MOCKSESSID=789; path=/; domain=example.com', 'MOCKSESSID=456; path=/')),
135 'different path' => array('MOCKSESSID=789; path=/foo', array('MOCKSESSID=789; path=/foo', 'MOCKSESSID=456; path=/')),
139 public function testUnstartedSessionIsNotSave()
141 $this->sessionHasNotBeenStarted();
142 $this->sessionMustNotBeSaved();
144 $this->filterResponse(new Request());
147 public function testDoesNotImplementServiceSubscriberInterface()
149 $this->assertTrue(interface_exists(ServiceSubscriberInterface::class));
150 $this->assertTrue(class_exists(SessionListener::class));
151 $this->assertTrue(class_exists(TestSessionListener::class));
152 $this->assertFalse(is_subclass_of(SessionListener::class, ServiceSubscriberInterface::class), 'Implementing ServiceSubscriberInterface would create a dep on the DI component, which eg Silex cannot afford');
153 $this->assertFalse(is_subclass_of(TestSessionListener::class, ServiceSubscriberInterface::class, 'Implementing ServiceSubscriberInterface would create a dep on the DI component, which eg Silex cannot afford'));
156 private function filterResponse(Request $request, $type = HttpKernelInterface::MASTER_REQUEST, Response $response = null)
158 $request->setSession($this->session);
159 $response = $response ?: new Response();
160 $kernel = $this->getMockBuilder('Symfony\Component\HttpKernel\HttpKernelInterface')->getMock();
161 $event = new FilterResponseEvent($kernel, $request, $type, $response);
163 $this->listener->onKernelResponse($event);
165 $this->assertSame($response, $event->getResponse());
170 private function sessionMustNotBeSaved()
172 $this->session->expects($this->never())
176 private function sessionMustBeSaved()
178 $this->session->expects($this->once())
182 private function sessionHasBeenStarted()
184 $this->session->expects($this->once())
185 ->method('isStarted')
186 ->will($this->returnValue(true));
189 private function sessionHasNotBeenStarted()
191 $this->session->expects($this->once())
192 ->method('isStarted')
193 ->will($this->returnValue(false));
196 private function sessionIsEmpty()
198 $this->session->expects($this->once())
200 ->will($this->returnValue(true));
203 private function fixSessionId($sessionId)
205 $this->session->expects($this->any())
207 ->will($this->returnValue($sessionId));
210 private function getSession()
212 $mock = $this->getMockBuilder('Symfony\Component\HttpFoundation\Session\Session')
213 ->disableOriginalConstructor()
216 // set return value for getName()
217 $mock->expects($this->any())->method('getName')->will($this->returnValue('MOCKSESSID'));