#34276: LocMemCache not working for multiple threads
-------------------------------+--------------------------------------
Reporter: dhiegomaga | Owner: nobody
Type: Bug | Status: new
Component: Uncategorized | Version: 4.1
Severity: Normal | Resolution:
Keywords: LocMemCache | Triage Stage: Unreviewed
Has patch: 0 | Needs documentation: 0
Needs tests: 0 | Patch needs improvement: 0
Easy pickings: 0 | UI/UX: 0
-------------------------------+--------------------------------------
Description changed by dhiegomaga:
Old description:
> I have a thread that is initialized on apps.py in a given app in django.
>
> This thread updates the value of a `counter` that is saved in cache,
> using `django.core.cache`.
>
> Also I have a view that returns the value of the same cache, in an
> endpoint:
>
> {{{
> # jobs.py
> import threading
> import time
> from django.core.cache import cache
>
> class MyThread:
> def __init__(self) -> None:
> self.t = threading.Thread(target=MyThread.receiverLoop, args=(self,))
> self.t.daemon = True
> self.count = 1
>
> def receiverLoop(self):
> global udpTempVar
> while self.running:
> time.sleep(3)
> self.count += 1
> cache.set('count', self.count)
>
> def start(self):
> self.running = True
> self.t.start()
>
> def stop(self):
> self.running = False
>
> # --------------
> # apps.py
> from django.apps import AppConfig
> import os
>
> class MyAppConfig(AppConfig):
> default_auto_field = "django.db.models.BigAutoField"
> name = "MyApp"
>
> def ready(self) -> None:
> from .jobs import MyThread
> t= MyThread()
>
> if os.environ.get('RUN_MAIN', None) != 'true':
> t.start()
> # return super().ready()
>
> # --------------
> # views.py
> from django.http import JsonResponse
> from django.core.cache import cache
> # ... other imports
>
> def getCurrentCount(request):
> global cache
> if request.method == 'GET':
> return JsonResponse({
> 'count': cache.get('count')
> })
> }}}
>
> I am using
> (LocMemCache)[https://docs.djangoproject.com/en/4.1/topics/cache/#local-
> memory-caching] in settings.py:
>
> {{{
> CACHES = {
> 'default': {
> 'BACKEND': 'django.core.cache.backends.locmem.LocMemCache',
> 'LOCATION': 'unique-snowflake',
> }
> }
> }}}
>
> But when I try to log the result of `cache.get('count')`, it returns
> `None`.
>
> The documentation clearly states:
>
> "This cache is **per-process** (see below) and thread-safe."
>
> "Note that each process will have its own private cache instance, which
> means no **cross-process caching is possible**. "
>
> I have the impression that they meant the cache is **per-thread** , not
> ** per-process** . Both my threads are on the same process, so they
> should share the same caching, according to the documentation. It also
> emphasizes, **no cross-process caching is possible**. It doesn't say **no
> cross-threading caching is possible**. But reading other resources I
> found online, it seems this is not shared even among threads, so the
> documentation is wrong, or there is a bug in this version of Django.
New description:
I have a thread that is initialized on apps.py in a given app in django.
This thread updates the value of a `counter` that is saved in cache, using
`django.core.cache`.
Also I have a view that returns the value of the same cache, in an
endpoint:
{{{
# jobs.py
import threading
import time
from django.core.cache import cache
class MyThread:
def __init__(self) -> None:
self.t = threading.Thread(target=MyThread.myLoop, args=(self,))
self.t.daemon = True
self.count = 1
def myLoop(self):
while self.running:
time.sleep(3)
self.count += 1
cache.set('count', self.count)
def start(self):
self.running = True
self.t.start()
def stop(self):
self.running = False
# --------------
# apps.py
from django.apps import AppConfig
import os
class MyAppConfig(AppConfig):
default_auto_field = "django.db.models.BigAutoField"
name = "MyApp"
def ready(self) -> None:
from .jobs import MyThread
t= MyThread()
if os.environ.get('RUN_MAIN', None) != 'true':
t.start()
# return super().ready()
# --------------
# views.py
from django.http import JsonResponse
from django.core.cache import cache
# ... other imports
def getCurrentCount(request):
global cache
if request.method == 'GET':
return JsonResponse({
'count': cache.get('count')
})
}}}
I am using
(LocMemCache)[https://docs.djangoproject.com/en/4.1/topics/cache/#local-
memory-caching] in settings.py:
{{{
CACHES = {
'default': {
'BACKEND': 'django.core.cache.backends.locmem.LocMemCache',
'LOCATION': 'unique-snowflake',
}
}
}}}
But when I try to log the result of `cache.get('count')`, it returns
`None`.
The documentation clearly states:
"This cache is **per-process** (see below) and thread-safe."
"Note that each process will have its own private cache instance, which
means no **cross-process caching is possible**. "
I have the impression that they meant the cache is **per-thread** , not **
per-process** . Both my threads are on the same process, so they should
share the same caching, according to the documentation. It also
emphasizes, **no cross-process caching is possible**. It doesn't say **no
cross-threading caching is possible**. But reading other resources I found
online, it seems this is not shared even among threads, so the
documentation is wrong, or there is a bug in this version of Django.
--
--
Ticket URL: <https://code.djangoproject.com/ticket/34276#comment:2>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.
--
You received this message because you are subscribed to the Google Groups
"Django updates" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/django-updates/01070185d004eb5e-9d2c8884-7054-4cb1-b12e-b9206f1f13a5-000000%40eu-central-1.amazonses.com.