Подтвердить что ты не робот

Кэш приложений/консоли Symfony: clear --env = prod и cache (APC, Memcached и т.д.)?

Я использую сервер Memcached (вместе с расширением PHP memcache) для кэширования метаданных валидатора и драйвера кэша метаданных/результата/запроса Doctrine.

Все работает так, как ожидалось, и быстро сравнивается с кешем файловой системы.

Мой вопрос в том, выполняет ли команда:

php app/console cache:clear --env=prod --no-debug

автоматически очистить все типы кеша (включая memcache)?

После выполнения этой команды и проверки статистики сервера количество элементов всегда совпадает с окном кэша:

enter image description here

Моя конфигурация, где% prod_cache% - фактически строка memcache:

# Framework Configuration
framework:
    validation:
        cache: %prod_cache% # Matches validator cache service

# Doctrine Configuration
doctrine:
    orm:
        metadata_cache_driver:
            type: service
            id: cache_%prod_cache%
        result_cache_driver:
            type: service
            id: cache_%prod_cache%
        query_cache_driver:
            type: service
            id: cache_%prod_cache%

# DoctrineCacheBundle Configuration
doctrine_cache:
    providers:
        memcache:
            type: memcache
            alias: cache_memcache

# Services
services:
    validator.mapping.cache.memcache: # Validator cache service
        class: Symfony\Component\Validator\Mapping\Cache\DoctrineCache
        arguments: [@cache_memcache]
4b9b3361

Ответ 1

кэша: прозрачный

Команда cache:clear не очищает кэширование Doctrine. Он очищает только некоторые специфические кэш-памяти Symfony 2, в основном каталоги app/cache (или var/cache).

Команды Doctrine

Чтобы очистить кэширование Doctrine, используйте:

  • doctrine:cache:clear-metadata --env=prod
  • doctrine:cache:clear-query --env=prod
  • doctrine:cache:clear-result --env=prod

Дополнительные кеши

Если вы используете дополнительные хранилища кешей, вам придется очистить их самостоятельно. Вы можете посмотреть команды doctrine:cache:clear-*, чтобы получить представление о том, как создать свою собственную команду.

Но, глядя на вашу конфигурацию, вы используете один кэш-хранилище для 3 кэшей доктрины и кэша проверки Symfony. Поэтому вызов только одного из doctrine:cache:clear-* должен очистить все.

Отключить тему

При использовании системы кэширования, такой как APC, OPcache и, возможно, другие, вам нужно будет понять, что при запуске PHP script из командной строки используется другое пространство памяти при запуске PHP скрипт с веб-сервера.

Другими словами: когда вы очищаете такие кэши из командной строки, кеши, используемые веб-сервером, не затрагиваются. Чтобы очистить кеши веб-сервера, вам нужно запустить очистку кэша script (s) с самого веб-сервера.

Это не проблема для memcached, потому что это отдельная программа, управляющая собственным пространством памяти.

Ответ 2

Вам нужно очистить внешний кеш из документа (SF 2.5):

Может быть много других вещей, которые вам нужно сделать, в зависимости от ваша настройка:         [...] Очистка кэша APC

Смотрите: http://symfony.com/doc/current/cookbook/deployment/tools.html#e-other-things

Ответ 3

Эта команда не очищает Memcache, поскольку она является автономным кэшем памяти. Он очищает только кеш Symfony. Чтобы очистить memcache, вы должны запускать вручную:

echo 'flush_all' | nc localhost 11211

Но я думаю, вы уже это знаете.

Ответ 4

Команды clear: cache только очищают кеш symfony в файловой системе, а затем разминают его. Вы можете использовать некоторые дополнительные пакеты для очистки других кешей:

Memcache: https://github.com/LeaseWeb/LswMemcacheBundle

APC: https://github.com/ornicar/ApcBundle

Ответ 5

Если вы проверите vendor/symfony/src/Symfony/Bundle/FrameworkBundle/Command/CacheClearCommand.php, вы увидите, что Symfony очищает кеш, используя службу файловой системы. Он очищает кеш, удаляя старый каталог.

Вот точная функция (Symfony 2.4)

    protected function execute(InputInterface $input, OutputInterface $output)
{
    $realCacheDir = $this->getContainer()->getParameter('kernel.cache_dir');
    $oldCacheDir  = $realCacheDir.'_old';
    $filesystem   = $this->getContainer()->get('filesystem');

    if (!is_writable($realCacheDir)) {
        throw new \RuntimeException(sprintf('Unable to write in the "%s" directory', $realCacheDir));
    }

    if ($filesystem->exists($oldCacheDir)) {
        $filesystem->remove($oldCacheDir);
    }

    $kernel = $this->getContainer()->get('kernel');
    $output->writeln(sprintf('Clearing the cache for the <info>%s</info> environment with debug <info>%s</info>', $kernel->getEnvironment(), var_export($kernel->isDebug(), true)));
    $this->getContainer()->get('cache_clearer')->clear($realCacheDir);

    if ($input->getOption('no-warmup')) {
        $filesystem->rename($realCacheDir, $oldCacheDir);
    } else {
        // the warmup cache dir name must have the same length than the real one
        // to avoid the many problems in serialized resources files
        $warmupDir = substr($realCacheDir, 0, -1).'_';

        if ($filesystem->exists($warmupDir)) {
            $filesystem->remove($warmupDir);
        }

        $this->warmup($warmupDir, $realCacheDir, !$input->getOption('no-optional-warmers'));

        $filesystem->rename($realCacheDir, $oldCacheDir);
        if (defined('PHP_WINDOWS_VERSION_BUILD')) {
            sleep(1);  // workaround for Windows PHP rename bug
        }
        $filesystem->rename($warmupDir, $realCacheDir);
    }

    $filesystem->remove($oldCacheDir);
}

Ответ 6

Если вы используете кеш, такой как APC, который использует различное пространство памяти для консоли и веб-сервера, у вас нет другого, почему бы вам и интерфейса, где вы вручную очищаете кеш.

Для memcache, memcached и т.д. вы можете подключиться к кешу: очистить команду, создав прослушиватель над событием kernel.cache_clearer, которое запускает команды очистки кэша доктрины.

Какой бы метод вы не использовали для очистки кеша, некоторые типы кешей, такие как memcache, не будут выпускать используемую память. Вместо этого они будут отключать ключ в следующий раз, когда команда get выдается на этом ключе или когда память заполнена, а некоторые ключи должны быть выведены.

class CacheClearDoctrineListener implements CacheClearerInterface
{
/**
 * @var ContainerInterface
 */
protected $container;

protected $environment;

public function setContainer(ContainerInterface $container = null)
{
    $this->container = $container;
    $this->environment = $container->get('kernel')->getEnvironment();
}

public function clear($cacheDir)
{
    $this->clearCacheMetadata();
    $this->clearCacheQuery();
}

protected function clearCacheMetadata()
{
    // clear cache metadata
    $application = new Application($this->container->get('kernel'));
    $application->setAutoExit(false);

    $output = new ConsoleOutput();
    $arguments = array(
        "command" => "doctrine:cache:clear-metadata",
        "--env" => $this->environment
    );
    $input = new ArrayInput($arguments);
    $returnCode = $application->run($input, $output);

    if ($returnCode != 0) {
        $output->writeln(json_decode(rtrim($output)));
    }
}

protected function clearCacheQuery()
{
    // clear cache query
    $application = new Application($this->container->get('kernel'));
    $application->setAutoExit(false);

    $output = new ConsoleOutput();
    $arguments = array(
        "command" => "doctrine:cache:clear-query",
        "--env" => $this->environment
    );
    $input = new ArrayInput($arguments);
    $returnCode = $application->run($input, $output);

    if ($returnCode != 0) {
        $output->writeln(json_decode(rtrim($output)));
    }
}
}

Объявите свое обслуживание примерно так:

<service id="cache_clear_doctrine_clearer" class="%namespace_of_your_listener%">
    <call method="setContainer">
        <argument type="service" id="service_container"/>
    </call>
    <tag name="kernel.cache_clearer"  priority="254" />
</service>

Ответ 7

попробуйте следующее:

php app/console memcached:clear --clearAll default