Skip to content

Commit ea729d8

Browse files
andreromdbu
authored andcommitted
Fix missing NoAutoCacheControl when vary on contex hash is set from Response (#485)
This moves logic to set NoAutoCacheControl so it is always executed if vary header exists, and not only we we add it in the listener.
1 parent 911bce4 commit ea729d8

File tree

2 files changed

+109
-4
lines changed

2 files changed

+109
-4
lines changed

src/EventListener/UserContextListener.php

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -198,10 +198,12 @@ public function onKernelResponse(FilterResponseEvent $event)
198198
&& !in_array($this->options['user_hash_header'], $vary)
199199
) {
200200
$vary[] = $this->options['user_hash_header'];
201-
if (4 <= Kernel::MAJOR_VERSION && 1 <= Kernel::MINOR_VERSION) {
202-
// header to avoid Symfony SessionListener overwriting the response to private
203-
$response->headers->set(AbstractSessionListener::NO_AUTO_CACHE_CONTROL_HEADER, 1);
204-
}
201+
}
202+
203+
// For Symfony 4.1+ if user hash header was in vary or just added here by "add_vary_on_hash"
204+
if (4 <= Kernel::MAJOR_VERSION && 1 <= Kernel::MINOR_VERSION && in_array($this->options['user_hash_header'], $vary)) {
205+
// header to avoid Symfony SessionListener overwriting the response to private
206+
$response->headers->set(AbstractSessionListener::NO_AUTO_CACHE_CONTROL_HEADER, 1);
205207
}
206208
} elseif ($this->options['add_vary_on_hash']) {
207209
/*

tests/Unit/EventListener/UserContextListenerTest.php

Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,9 @@
2020
use Symfony\Component\HttpFoundation\Response;
2121
use Symfony\Component\HttpKernel\Event\FilterResponseEvent;
2222
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
23+
use Symfony\Component\HttpKernel\EventListener\AbstractSessionListener;
2324
use Symfony\Component\HttpKernel\HttpKernelInterface;
25+
use Symfony\Component\HttpKernel\Kernel;
2426

2527
class UserContextListenerTest extends TestCase
2628
{
@@ -182,6 +184,107 @@ public function testOnKernelResponse()
182184
$this->assertContains('X-Hash', $event->getResponse()->headers->get('Vary'));
183185
}
184186

187+
public function testOnKernelResponseSetsNoAutoCacheHeader()
188+
{
189+
if (4 > Kernel::MAJOR_VERSION || 1 > Kernel::MINOR_VERSION) {
190+
$this->markTestSkipped('Test only relevant for Symfony 4.1 and up');
191+
}
192+
193+
$request = new Request();
194+
$request->setMethod('HEAD');
195+
$request->headers->set('X-User-Context-Hash', 'hash');
196+
197+
$hashGenerator = \Mockery::mock(HashGenerator::class);
198+
199+
$userContextListener = new UserContextListener(
200+
$this->getRequestMatcher($request, false),
201+
$hashGenerator
202+
);
203+
$event = $this->getKernelResponseEvent($request);
204+
205+
$userContextListener->onKernelResponse($event);
206+
207+
$this->assertContains('X-User-Context-Hash', $event->getResponse()->headers->get('Vary'));
208+
$this->assertEquals(1, $event->getResponse()->headers->get(AbstractSessionListener::NO_AUTO_CACHE_CONTROL_HEADER));
209+
}
210+
211+
public function testOnKernelResponseSetsNoAutoCacheHeaderWhenCustomHeader()
212+
{
213+
if (4 > Kernel::MAJOR_VERSION || 1 > Kernel::MINOR_VERSION) {
214+
$this->markTestSkipped('Test only relevant for Symfony 4.1 and up');
215+
}
216+
217+
$request = new Request();
218+
$request->setMethod('HEAD');
219+
$request->headers->set('X-User-Context-Hash', 'hash');
220+
221+
$hashGenerator = \Mockery::mock(HashGenerator::class);
222+
223+
$userContextListener = new UserContextListener(
224+
$this->getRequestMatcher($request, false),
225+
$hashGenerator
226+
);
227+
$event = $this->getKernelResponseEvent($request, new Response('', 200, ['Vary' => 'X-User-Context-Hash']));
228+
229+
$userContextListener->onKernelResponse($event);
230+
231+
$this->assertEquals(1, $event->getResponse()->headers->get(AbstractSessionListener::NO_AUTO_CACHE_CONTROL_HEADER));
232+
}
233+
234+
public function testOnKernelResponseSetsNoAutoCacheHeaderWhenCustomHeaderAndNoAddVaryOnHash()
235+
{
236+
if (4 > Kernel::MAJOR_VERSION || 1 > Kernel::MINOR_VERSION) {
237+
$this->markTestSkipped('Test only relevant for Symfony 4.1 and up');
238+
}
239+
240+
$request = new Request();
241+
$request->setMethod('HEAD');
242+
$request->headers->set('X-User-Context-Hash', 'hash');
243+
244+
$hashGenerator = \Mockery::mock(HashGenerator::class);
245+
246+
$userContextListener = new UserContextListener(
247+
$this->getRequestMatcher($request, false),
248+
$hashGenerator,
249+
null,
250+
[
251+
'add_vary_on_hash' => false,
252+
]
253+
);
254+
$event = $this->getKernelResponseEvent($request, new Response('', 200, ['Vary' => 'X-User-Context-Hash']));
255+
256+
$userContextListener->onKernelResponse($event);
257+
258+
$this->assertEquals(1, $event->getResponse()->headers->get(AbstractSessionListener::NO_AUTO_CACHE_CONTROL_HEADER));
259+
}
260+
261+
public function testOnKernelResponseDoesNotSetNoAutoCacheHeaderWhenNoCustomHeaderAndNoAddVaryOnHash()
262+
{
263+
if (4 > Kernel::MAJOR_VERSION || 1 > Kernel::MINOR_VERSION) {
264+
$this->markTestSkipped('Test only relevant for Symfony 4.1 and up');
265+
}
266+
267+
$request = new Request();
268+
$request->setMethod('HEAD');
269+
$request->headers->set('X-User-Context-Hash', 'hash');
270+
271+
$hashGenerator = \Mockery::mock(HashGenerator::class);
272+
273+
$userContextListener = new UserContextListener(
274+
$this->getRequestMatcher($request, false),
275+
$hashGenerator,
276+
null,
277+
[
278+
'add_vary_on_hash' => false,
279+
]
280+
);
281+
$event = $this->getKernelResponseEvent($request);
282+
283+
$userContextListener->onKernelResponse($event);
284+
285+
$this->assertFalse($event->getResponse()->headers->has(AbstractSessionListener::NO_AUTO_CACHE_CONTROL_HEADER));
286+
}
287+
185288
public function testOnKernelResponseNotMaster()
186289
{
187290
$request = new Request();

0 commit comments

Comments
 (0)