Opened 3 weeks ago
Closed 9 days ago
#36879 closed Cleanup/optimization (fixed)
Add Django cache identification to Redis client metadata
| Reported by: | Vasil Chomakov | Owned by: | ar3ph |
|---|---|---|---|
| Component: | Core (Cache system) | Version: | dev |
| Severity: | Normal | Keywords: | redis cache observability |
| Cc: | Vasil Chomakov, ar3ph | Triage Stage: | Ready for checkin |
| Has patch: | yes | Needs documentation: | no |
| Needs tests: | no | Patch needs improvement: | no |
| Easy pickings: | no | UI/UX: | no |
Description (last modified by )
Proposal: Add Django cache identification to Redis client metadata
Context
Redis documentation recommends that clients identify themselves via connection metadata to help operators monitor, debug, and reason about production systems (for example using CLIENT SETINFO / CLIENT INFO):
https://redis.io/docs/latest/commands/client-setinfo/
This information is intended to help Redis operators understand what software is connecting to their servers, especially in shared or multi-tenant environments.
Django’s Redis cache backend is built on top of redis-py, which means Redis connections created by Django are currently indistinguishable from other redis-py-based clients in shared Redis deployments. This makes it harder for Redis operators to attribute traffic, diagnose issues, or understand cache usage patterns when multiple applications or frameworks share the same Redis instance.
Proposal
Django could provide additional, non-invasive client identification for Redis cache connections to indicate that the connection originates from Django’s cache framework.
redis-py exposes a driver_info API that may be used to attach Django-specific context to the connection, in line with Redis’s client identification recommendations.
Goals
- Align with Redis client identification best practices
- Allow Redis operators to distinguish Django cache connections
- Improve observability in shared Redis environments
Example (illustrative)
A Redis connection created by Django’s cache backend might expose metadata equivalent to:
- Client library:
redis-py - Framework:
django-cache
Scope
- This is a feature proposal, not a patch submission
- No behavioral changes to caching semantics are proposed
- Any implementation would rely solely on
redis-py’s supported APIs
Change History (17)
comment:1 by , 3 weeks ago
| Description: | modified (diff) |
|---|
comment:2 by , 3 weeks ago
comment:3 by , 3 weeks ago
| Cc: | added |
|---|
comment:4 by , 3 weeks ago
or I can make it default to use driver_info when lib_name and lib_ver are no longer supported.
comment:5 by , 3 weeks ago
| Has patch: | set |
|---|
follow-up: 8 comment:6 by , 3 weeks ago
I suggest using DriverInfo when available (can be successfully imported) and falling back to lib_name and lib_version if redis-py does not yet support it.
IMPORTANT: Note that when manually set, lib_name and lib_version should look like this:
lib_name=redis-py(django-cache_v{django-cache-version})lib_version={redis-py-version}
per Redis CLIENT SETINFO documentation: https://redis.io/docs/latest/commands/client-setinfo/
comment:7 by , 3 weeks ago
Here is a django-redis example. Perhaps the best solution is to just change the lib-name to include our upstream driver.
The lib-name will become like redis-py(django_v6.1.0)
comment:8 by , 3 weeks ago
Replying to Vasil Chomakov:
I suggest using
DriverInfowhen available (can be successfully imported) and falling back tolib_nameandlib_versionifredis-pydoes not yet support it.
IMPORTANT: Note that when manually set,
lib_nameandlib_versionshould look like this:
lib_name=redis-py(django-cache_v{django-cache-version})lib_version={redis-py-version}per Redis
CLIENT SETINFOdocumentation: https://redis.io/docs/latest/commands/client-setinfo/
Should the driver be called django-cache? My opinion is to just call it django, b/c django-cache is not a separated package.
follow-up: 10 comment:9 by , 3 weeks ago
I agree, django_v{django-version} is descriptive enough.
So when using DriverInfo, just setting the upstream driver to django_v6.1.0 would suffice.
When DriverInfo is not available:
lib_name=redis-py(django_v6.1.0)lib_version={redis-py-version}
comment:10 by , 3 weeks ago
Replying to Vasil Chomakov:
I agree,
django_v{django-version}is descriptive enough.
So when usingDriverInfo, just setting the upstream driver todjango_v6.1.0would suffice.
WhenDriverInfois not available:
lib_name=redis-py(django_v6.1.0)lib_version={redis-py-version}
I finished this in the proposed PR. Note that lib_version defaults to redis-py version. So nothing for us to do there.
comment:11 by , 3 weeks ago
| Owner: | set to |
|---|---|
| Status: | new → assigned |
comment:12 by , 3 weeks ago
| Owner: | changed from to |
|---|
comment:13 by , 13 days ago
| Patch needs improvement: | set |
|---|---|
| Triage Stage: | Unreviewed → Accepted |
| Type: | New feature → Cleanup/optimization |
The request makes sense, but I'm not sure we've identified the least invasive solution.
comment:15 by , 13 days ago
I've updated my PR to avoid dynamic class creation, only changing the pool_options now as a better alternative.
comment:16 by , 10 days ago
| Patch needs improvement: | unset |
|---|---|
| Triage Stage: | Accepted → Ready for checkin |
I poked around and got a working solution. Although in future versions of
redis-py,lib_nameandlib_versionare deprecated,DriverInfois not available for latestredis-pyreleasev7.1.0.In
django/core/cache/backends/redis.py:class RedisCacheClient: def _get_connection_class(self, lib): class DjangoConnection(lib.Connection): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.lib_name = "django" self.lib_version = django.get_version() return DjangoConnection def __init__( servers, serializer=None, pool_class=None, parser_class=None, **options, ): ... self._connection_class = self._get_connection_class(self._lib) ... self._pool_options = { "parser_class": parser_class, "connection_class": self._connection_class, **options, }I can make a PR once this ticket is accepted. And we'll have to update again once
DriverInfoforredis-pyis released.