diff --git a/ChangeLog b/ChangeLog index e38a3b651..7c8a7d443 100644 --- a/ChangeLog +++ b/ChangeLog @@ -12,7 +12,9 @@ What's New in astroid 2.12.10? ============================== Release date: TBA +* ``decorators.cached`` now gets its cache cleared by calling ``AstroidManager.clear_cache``. + Refs #1780 What's New in astroid 2.12.9? ============================= diff --git a/astroid/_cache.py b/astroid/_cache.py new file mode 100644 index 000000000..fc4ddc205 --- /dev/null +++ b/astroid/_cache.py @@ -0,0 +1,26 @@ +# Licensed under the LGPL: https://www.gnu.org/licenses/old-licenses/lgpl-2.1.en.html +# For details: https://github.com/PyCQA/astroid/blob/main/LICENSE +# Copyright (c) https://github.com/PyCQA/astroid/blob/main/CONTRIBUTORS.txt + +from __future__ import annotations + +from typing import Any + + +class CacheManager: + """Manager of caches, to be used as a singleton.""" + + def __init__(self) -> None: + self.dict_caches: list[dict[Any, Any]] = [] + + def clear_all_caches(self) -> None: + """Clear all caches.""" + for dict_cache in self.dict_caches: + dict_cache.clear() + + def add_dict_cache(self, cache: dict[Any, Any]) -> None: + """Add a dictionary cache to the manager.""" + self.dict_caches.append(cache) + + +CACHE_MANAGER = CacheManager() diff --git a/astroid/decorators.py b/astroid/decorators.py index c4f44dcd2..e9cc3292c 100644 --- a/astroid/decorators.py +++ b/astroid/decorators.py @@ -15,7 +15,7 @@ import wrapt -from astroid import util +from astroid import _cache, util from astroid.context import InferenceContext from astroid.exceptions import InferenceError @@ -34,6 +34,7 @@ def cached(func, instance, args, kwargs): cache = getattr(instance, "__cache", None) if cache is None: instance.__cache = cache = {} + _cache.CACHE_MANAGER.add_dict_cache(cache) try: return cache[func] except KeyError: diff --git a/astroid/manager.py b/astroid/manager.py index 25373a6b4..ff472256f 100644 --- a/astroid/manager.py +++ b/astroid/manager.py @@ -16,6 +16,7 @@ from importlib.util import find_spec, module_from_spec from typing import TYPE_CHECKING, ClassVar +from astroid._cache import CACHE_MANAGER from astroid.const import BRAIN_MODULES_DIRECTORY from astroid.exceptions import AstroidBuildingError, AstroidImportError from astroid.interpreter._import import spec, util @@ -382,6 +383,8 @@ def clear_cache(self) -> None: # NB: not a new TransformVisitor() AstroidManager.brain["_transform"].transforms = collections.defaultdict(list) + CACHE_MANAGER.clear_all_caches() + for lru_cache in ( LookupMixIn.lookup, _cache_normalize_path_,