В нашем проекте Symfony есть виджет входа в систему, который, как мне сказали, должен загружаться через AJAX, чтобы не вмешиваться в кеширование страниц.
Он отображает либо «Войти», либо адрес электронной почты пользователя, если он уже вошел в систему.
Проблема в том, что этот шаблон веточки также кешируется! Так что загрузка через ajax не помогла.
Как я могу сказать Twig каждый раз отображать мой шаблон с нуля, не отключая кеширование всего сайта?
Сам шаблон если очень простой:
<small id = "login-username">
{% if is_granted('ROLE_USER') %}
{{ app.user.username }}
{% else %}
{{ 'LoginWidgetElement.login' | trans }}
{% endif %}
</small>
Класс элемента тоже очень простой:
<?php
namespace Xyz\Sports\Element\LoginWidget;
use Xyz\Library\AbstractElement;
use Sensio\Bundle\FrameworkExtraBundle\Configuration as Config;
/**
* @Config\Template("@LoginWidgetElement/login_widget.html.twig")
*/
class LoginWidgetElement extends AbstractElement
{
public function render()
{
return [];
}
public function renderPreview()
{
return $this->render();
}
}
UPDATE
Кажется, что шаблон веточки проверяется, поэтому я попытался отправить ответ, сообщающий браузеру не кэшировать, но все равно требуется около 15 запросов, прежде чем переменная изменится !! ??
Кеш Twig:
<small id=\"login-username\">
";
// line 9
if ($this->extensions['Symfony\Bridge\Twig\Extension\SecurityExtension']->isGranted("ROLE_USER")) {
// line 10
echo " ";
echo twig_escape_filter($this->env, twig_get_attribute($this->env, $this->source, twig_get_attribute($this->env, $this->source, (isset($context["app"]) || array_key_exists("app", $context) ? $context["app"] : (function () { throw new Twig_Error_Runtime('Variable "app" does not exist.', 10, $this->source); })()), "user", array()), "username", array()), "html", null, true);
echo "
";
} else {
// line 12
echo " ";
echo twig_escape_filter($this->env, $this->extensions['Symfony\Bridge\Twig\Extension\TranslationExtension']->trans("LoginWidgetElement.login"), "html", null, true);
echo "
";
}
// line 14
echo " </small>
Итак, есть проверка isGranted('ROLE_USER'). Теперь в моем методе рендеринга:
$response = new Response();
$response->headers->set('Cache-Control', 'no-store, no-cache, must-revalidate, max-age=0, post-check=0, pre-check=0');
$response->headers->set('Pragma', 'no-cache');
$body = $this->twig->render('@LoginWidgetElement/login_widget.html.twig');
$response->setContent($body);
return $response;
Однако сигары по-прежнему нет: '- (
спасибо fucethebads, но этот метод устарел и удален ;-(






Похоже, установка заголовков кеша имеет собственный метод, и мы не должны просто использовать $response->headers->set($key, $val);.
Я переместил логику в многоразовую черту:
<?php
namespace Xyz\Library\Traits;
use Symfony\Component\HttpFoundation\Response;
trait NoCacheHeadersTrait
{
public function disableBrowserCache(Response $response) : Response
{
$response->headers->addCacheControlDirective('no-store', true);
$response->headers->addCacheControlDirective('no-cache', true);
$response->headers->addCacheControlDirective('must-revalidate', true);
$response->headers->addCacheControlDirective('max-age', 0);
$response->headers->addCacheControlDirective('post-check', 0);
$response->headers->addCacheControlDirective('pre-check', 0);
$response->headers->set('Pragma', 'no-cache');
return $response;
}
}
И теперь я use трейт в классе, и в моем методе рендеринга он теперь выглядит так:
public function render()
{
$response = $this->disableBrowserCache(new Response());
$body = $this->twig->render('@LoginWidgetElement/login_widget.html.twig');
$response->setContent($body);
return $response;
}