Создайте класс провайдера кэша в Symfony - PullRequest
0 голосов
/ 29 октября 2018

В нашем приложении Symfony 3.4 есть memcache:

cache:
    app: cache.adapter.memcached
    default_memcached_provider: "%app.memcached.dsn%"

Однако нас попросили использовать несколько серверов кэширования, поэтому просто передать один DSN не годится.

Глядя здесь (https://symfony.com/blog/new-in-symfony-3-3-memcached-cache-adapter), Я вижу, вы можете создать его в коде, подобном этому:

$client = MemcachedAdapter::createConnection(array(
    // format => memcached://[user:pass@][ip|host|socket[:port]][?weight=int]
    // 'weight' ranges from 0 to 100 and it's used to prioritize servers
    'memcached://my.server.com:11211'
    'memcached://rmf:abcdef@localhost'
    'memcached://127.0.0.1?weight=50'
    'memcached://username:the-password@/var/run/memcached.sock'
    'memcached:///var/run/memcached.sock?weight=20'
)); 

Однако, это не автоматическое соединение.

Я считаю, что нам нужно либо создать класс провайдера, либо каким-то образом заставить его совершать вызовы addServer($dsn) после его создания. Я также видел следующие случайные сообщения:

memcache:
    class: Memcached
    calls:
        - [ addServer, [ %app.memcached.dsn.1% ]]
        - [ addServer, [ %app.memcached.dsn.2% ]]

Однако это не очень помогает, или я что-то упустил.

Кто-нибудь может помочь? Как мне создать этот класс провайдера?

Ответы [ 2 ]

0 голосов
/ 19 марта 2019

Для одного из моих проектов с Symfony 3.4 конфигурация была проще:

Создайте сервис, который будет использоваться в качестве клиента:

app.memcached_client:
    class: Memcached
    factory: ['AppBundle\Services\Memcached', 'createConnection']
    arguments: ['memcached://%memcache_ip%:%memcache_port%']

В AppBundle\Services\Memcached может быть вся необходимая мне логика:

class Memcached
{
    public static function createConnection($dns)
    {
        $options = [
            'persistent_id' => 'some id'
        ];

        // Some more custom logic. Maybe adding some custom options
        // For example for AWS Elasticache

        if (defined('Memcached::OPT_CLIENT_MODE') && defined('Memcached::DYNAMIC_CLIENT_MODE')) {
            $options['CLIENT_MODE'] = \Memcached::DYNAMIC_CLIENT_MODE;
        }

        return \Symfony\Component\Cache\Adapter\MemcachedAdapter::createConnection($dns, $options);
    }
}

И затем я использовал этот сервис в моем config.yml:

framework:
    cache:
        default_memcached_provider: app.memcached_client
0 голосов
/ 29 октября 2018

Вы можете скопировать приведенный выше фрагмент кода в качестве конфигурации службы в ваш services.yaml, который, вероятно, выглядит примерно так:

# app/config/services.yaml

services:
    app.memcached_client:
        class: Memcached
        factory: 'Symfony\Component\Cache\Adapter\MemcachedAdapter::createConnection'
        arguments: [['memcached://my.server.com:11211', 'memcached://rmf:abcdef@localhost']]

    app.memcached_adapter:
        class: Symfony\Component\Cache\Adapter\MemcachedAdapter
        arguments:
            - '@app.memcached_client'

Тогда в вашей конфигурации вы сможете ссылаться на адаптер, используя клиент, созданный на заводе, например, что-то вроде:

# app/config/config.yaml

framework:
    cache:
        app: app.memcached_adapter

Вы также можете перезаписать псевдоним по умолчанию cache.adapter.memcached вместо использования собственного адаптера.

Ваш подход, использующий Memcached::addServer, может также работать, но, как и в случае MemcachedAdapter::createConnection, это вернет клиента, который должен быть передан адаптеру кэша. Вот почему существует второй сервис app.memcached_adapter, который используется в конфигурации кеша.

Имейте в виду, что я не проверял это, так что это скорее грубый набросок, чем полностью работающее решение,

...