How to make Laravel work with Redis cluster on AWS

后端 未结 1 1327
無奈伤痛
無奈伤痛 2020-12-20 00:36

I\'m trying to use Laravel (5.4) with a clustered version of Redis. I followed the instructions form this post like so:

/*
|---------------------------------         


        
相关标签:
1条回答
  • 2020-12-20 00:48

    after searching and debugging, this is what made it work:

    'redis' => [
        'client' => 'predis',
        'cluster' => true,
        'options' => [
            'cluster' => 'redis',
            'parameters' => [
                'host' => env('REDIS_DEFAULT_HOST', '127.0.01'),
                'password' => env('REDIS_PASSWORD', null),
                'port' => env('REDIS_DEFAULT_PORT', 6379),
                'database' => 0,
                ],
            ],
        'clusters' => [
             'default' => [
                'host' => env('REDIS_DEFAULT_HOST', '127.0.01'),
                'password' => env('REDIS_PASSWORD', null),
                'port' => env('REDIS_DEFAULT_PORT', 6379),
                'database' => 0,
            ],
            'jobs' => [
                'host' => env('REDIS_JOBS_HOST', '127.0.01'),
                'password' => env('REDIS_PASSWORD', null),
                'port' => env('REDIS_JOBS_PORT', 6379),
                'database' => 0,
            ],
            'content' => [
                'host' => env('REDIS_CONTENT_HOST', '127.0.01'),
                'password' => env('REDIS_PASSWORD', null),
                'port' => env('REDIS_CONTENT_PORT', 6379),
                'database' => 0,
            ],
            'options' => [
                'cluster' => 'redis'
            ],
        ]
    ]
    

    note: one obvious mistake in my config in the above question was that i combined the host and port, which i fixed here. this is what my .env file looks like:

    REDIS_DEFAULT_HOST=127.0.0.1
    REDIS_JOBS_HOST=127.0.0.1
    REDIS_CONTENT_HOST=127.0.0.1
    
    REDIS_DEFAULT_PORT=7000
    REDIS_JOBS_PORT=7001
    REDIS_CONTENT_PORT=7002
    

    note: i created the cluster using the instructions here: https://redis.io/topics/cluster-tutorial#creating-the-cluster

    Research Methodology

    Due to the fact that: 1. The laravel/predis documentation on this is lacking 2. Most of the answers on stack overflow are along these lines: after googling and searching.. this is what worked out for me without much explanation of what's going on

    I figured I can help out a bit by showing how I found my answer to the above.

    1) Solving the error problem

    To solve this bug

    local.ERROR: Symfony\Component\Debug\Exception\FatalThrowableError: Type error: Argument 1 passed to Predis\Connection\Parameters::__construct() must be of the type array, integer given, called in /Users/Shared/dev/php/toters-api/vendor/predis/predis/src/Connection/Factory.php on line 164 in /Users/Shared/dev/php/toters-api/vendor/predis/predis/src/Connection/Parameters.php:34 Stack trace:

    I realized that my config/database.php format was simply wrong. Googling all over didn't give me any clear picture, so I decided to use xdebug and dive into the code. Note: I had the error stack trace (shown in the question above) printed in one doc, and I used that as a bird's eye view to guide me through the debug steps (ie stepping over/into/out etc while always printing the outputs in a separate doc and comparing it with my config/database.php as a sanity check/debug compass).

    After digging and printig, I came across this:

    [ *Locals ] [ Superglobals ] [ User defined constants ]
    
    - Locals at /Users/Shared/dev/php/toters-api/vendor/predis/predis/src/Client.php:55
    
     ▾ $options = (array [1])
      \
       ⬦ $options["cluster"] = (string [5]) `redis`
      /
     ▾ $parameters = (array [4])
      \
       ⬦ $parameters[0] = (string [14]) `127.0.0.1:7000`
       |
       ⬦ $parameters[1] = (null)
       |
       ⬦ $parameters[2] = (int) 6379
       |
       ⬦ $parameters[3] = (int) 0
      /
     ▾ $this = (Predis\Client [3])
      \
       ⬦ $this->connection = (null)
       |
       ⬦ $this->options = (null)
       |
       ⬦ $this->profile = (null)
      /
    

    I compared this with my .env file's contents:

    REDIS_DEFAULT_HOST=127.0.0.1:7000
    REDIS_JOBS_HOST=127.0.0.1:7001
    REDIS_CONTENT_HOST=127.0.0.1:7002
    

    and I realized that the format was wrong, I shouldn't put the host AND port in the same env variable.. so I put it like so instead:

    REDIS_DEFAULT_HOST=127.0.0.1
    REDIS_JOBS_HOST=127.0.0.1
    REDIS_CONTENT_HOST=127.0.0.1
    
    REDIS_DEFAULT_PORT=7000
    REDIS_JOBS_PORT=7001
    REDIS_CONTENT_PORT=7002
    

    and that solved my first problem.

    2) solving the other problems

    after the above was fixed i got this

    CLUSTERDOWN Hash slot not served

    this was was quite easy, it was just a matter of googling the error message (since the error message was clearly a native redis error message, rather than some cryptic library wrapper like predis error message).. and i found this answer.

    The rest was easy.

    0 讨论(0)
提交回复
热议问题