Add global and local set of ignored context keys

Closes #11234
This commit is contained in:
Nicolas Évrard
2023-02-06 18:40:00 +01:00
parent c989938e68
commit 967a41f467
4 changed files with 44 additions and 6 deletions
+1
View File
@@ -1,3 +1,4 @@
* Add local and global list of ignore context keys
* Add functions in transaction for check access and active record
* Add check_access and active_records attribute to Transaction
* Add searchable and sortable methods on Field
+2 -1
View File
@@ -4,7 +4,7 @@
Cache
=====
.. class:: Cache(name[, size_limit[, duration[, context]]])
.. class:: Cache(name[, size_limit[, duration[, context[, context_ignored_keys]]]])
Use to cache values between server requests.
@@ -19,6 +19,7 @@ Cache
And the ``context`` parameter is used to indicate if the cache depends on
the user context and is ``True`` by default.
Keys specified in ``context_ignored_keys`` are ignored.
The cache is cleaned on :class:`~trytond.transaction.Transaction` starts and
resets on :class:`~trytond.transaction.Transaction` commit or rollback.
+16 -5
View File
@@ -64,11 +64,23 @@ def _get_modules(cursor):
class BaseCache(object):
_instances = {}
context_ignored_keys = {
'client', '_request', '_check_access', '_skip_warnings',
}
def __init__(self, name, size_limit=1024, duration=None, context=True):
def __init__(
self, name, size_limit=1024, duration=None, context=True,
context_ignored_keys=None):
assert ((context_ignored_keys is not None and context)
or (context_ignored_keys is None)), (
f"context_ignored_keys ({context_ignored_keys}) is not valid"
f" in regards to context ({context}).")
self._name = name
self.size_limit = size_limit
self.context = context
self.context_ignored_keys = set()
if context and context_ignored_keys:
self.context_ignored_keys.update(context_ignored_keys)
self.hit = self.miss = 0
if isinstance(duration, dt.timedelta):
self.duration = duration
@@ -93,10 +105,9 @@ class BaseCache(object):
def _key(self, key):
if self.context:
context = Transaction().context.copy()
context.pop('client', None)
context.pop('_request', None)
context.pop('_check_access', None)
context.pop('_skip_warnings', None)
for k in (self.__class__.context_ignored_keys
| self.context_ignored_keys):
context.pop(k, None)
return (key, Transaction().user, freeze(context))
return key
+25
View File
@@ -15,6 +15,9 @@ from trytond.transaction import Transaction
cache = MemoryCache('test.cache')
cache_expire = MemoryCache('test.cache_expire', duration=1)
cache_ignored_local_context = MemoryCache(
'test.cache.ignored.local', context_ignored_keys={'ignored'})
cache_ignored_global_context = MemoryCache('test.cache.ignored.global')
class CacheTestCase(unittest.TestCase):
@@ -64,6 +67,28 @@ class CacheTestCase(unittest.TestCase):
with self.subTest(value=value):
self.assertEqual(unfreeze(value), result)
@with_transaction()
def test_ignored_context_key_global(self):
"Test global keys are ignored from context"
with Transaction().set_context(client='foo'):
cache_ignored_global_context.set('key', 0)
with Transaction().set_context(client='bar'):
value = cache_ignored_global_context.get('key')
self.assertEqual(value, 0)
@with_transaction()
def test_ignored_context_key_local(self):
"Test local keys are ignored from context"
with Transaction().set_context(ignored='foo'):
cache_ignored_local_context.set('key', 1)
with Transaction().set_context(ignored='bar'):
value = cache_ignored_local_context.get('key')
self.assertEqual(value, 1)
class MemoryCacheTestCase(unittest.TestCase):
"Test Cache"