Description
Describe the bug
We are trying to use django redis cache with sentinel and SSL connection in our application. The issue occurs when we use rediss
as part of the URL given in the LOCATION
setting, as described below.
To Reproduce
Keep the CACHES setting on settings.py as follows:
# there our other settings which we take from .env too, but mentioning this here for clarity
REDIS_SSL = env("REDIS_SSL", bool, default=False)
# in our case, since REDIS_SSL is true, REDIS_PROTOCOL would be 'rediss'
REDIS_PROTOCOL = "rediss" if REDIS_SSL else "redis"
CACHES = {
"default": {
"BACKEND": "django_redis.cache.RedisCache",
# The next line is where the issue occurs since we use REDIS_PROTOCOL
# which is 'rediss' in this case.
"LOCATION": f"{REDIS_PROTOCOL}://{REDIS_MASTER}/{REDIS_DB}",
"OPTIONS": {
"CLIENT_CLASS": "django_redis.client.SentinelClient",
"SENTINELS": SENTINELS,
"SENTINEL_KWARGS": {
"password": SENTINEL_PASSWORD,
"ssl_certfile": REDIS_SSL_CERTFILE,
"ssl_keyfile": REDIS_SSL_KEYFILE,
"ssl_ca_certs": REDIS_SSL_CA_CERTS,
"ssl_cert_reqs": None,
"ssl": REDIS_SSL,
},
"SOCKET_TIMEOUT": SENTINEL_CONNECTION_TIMEOUT,
"SOCKET_CONNECT_TIMEOUT": SENTINEL_CONNECTION_TIMEOUT,
"CONNECTION_POOL_CLASS": "redis.sentinel.SentinelConnectionPool",
"PASSWORD": REDIS_PASSWORD,
"CONNECTION_POOL_KWARGS": {
"ssl": REDIS_SSL,
**(
{
"ssl_certfile": REDIS_SSL_CERTFILE,
"ssl_keyfile": REDIS_SSL_KEYFILE,
"ssl_ca_certs": REDIS_SSL_CA_CERTS,
"ssl_cert_reqs": None,
}
if REDIS_SSL
else {}
),
},
},
"KEY_PREFIX": "cache",
"TIMEOUT": CACHE_TIMEOUT,
},
}
Note that we take the settings such as REDIS_MASTER, REDIS_DB etc from our environment file (.env), which we read using the django-environ library.
Expected behavior
The library should be able to connect to the sentinel-based setup and the application should start up properly on running the server.
Stack trace
Traceback (most recent call last):
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/redis/connection.py", line 1435, in get_connection
connection = self._available_connections.pop()
IndexError: pop from empty list
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/home/soham/aistudio/aeli_utils/cache.py", line 47, in get_from_cache
return cache.get(key, default)
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/django_redis/cache.py", line 91, in get
value = self._get(key, default, version, client)
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/django_redis/cache.py", line 31, in _decorator
return method(self, *args, **kwargs)
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/django_redis/cache.py", line 98, in _get
return self.client.get(key, default=default, version=version, client=client)
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/django_redis/client/default.py", line 258, in get
value = client.get(key)
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/redis/commands/core.py", line 1790, in get
return self.execute_command("GET", name)
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/redis/client.py", line 1255, in execute_command
conn = self.connection or pool.get_connection(command_name, **options)
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/redis/connection.py", line 1437, in get_connection
connection = self.make_connection()
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/redis/connection.py", line 1479, in make_connection
def release(self, connection):
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/redis/connection.py", line 1085, in __init__
super().__init__(**kwargs)
File "/home/soham/envs/aistudio/lib/python3.9/site-packages/redis/connection.py", line 941, in __init__
super().__init__(**kwargs)
TypeError: __init__() got an unexpected keyword argument 'connection_pool'
Environment (please complete the following information):
- Python version: 3.9
- Django Redis Version: 5.0.0
- Django Version: 3.2.6
- Redis Version: 7.0.10
- redis-py Version: 4.5.4
Additional context
Instead of keeping the LOCATION as f"{REDIS_PROTOCOL}://{REDIS_MASTER}/{REDIS_DB}"
, if we keep it as f"redis://{REDIS_MASTER}/{REDIS_DB}"
, the application works as expected. We are confused as to why we need to keep the protocol as redis
even though we clearly want to use rediss
.