1
0
mirror of https://github.com/django/django.git synced 2025-04-14 12:24:36 +00:00

Added: new function to FileBaseCaching, check() and refactored functions in caches.py

This commit is contained in:
almaz amanzholuly 2024-03-24 04:58:15 +05:00
parent 0574a576ea
commit 0610a5a5cb
3 changed files with 53 additions and 36 deletions

View File

@ -388,8 +388,11 @@ class BaseCache:
async def aclose(self, **kwargs):
pass
def check(self):
return []
def check(self, **kwargs):
raise NotImplementedError(
"subclasses may provide a check() method to verify the finder is "
"configured correctly."
)
memcached_error_chars_re = _lazy_re_compile(r"[\x00-\x20\x7f]")

View File

@ -2,6 +2,7 @@
import glob
import os
import pickle
import pathlib
import random
import tempfile
import time
@ -11,7 +12,7 @@ from hashlib import md5
from django.core.cache.backends.base import DEFAULT_TIMEOUT, BaseCache
from django.core.files import locks
from django.core.files.move import file_move_safe
from django.core.checks import Warning
class FileBasedCache(BaseCache):
cache_suffix = ".djcache"
@ -168,3 +169,21 @@ class FileBasedCache(BaseCache):
os.path.join(self._dir, fname)
for fname in glob.glob1(self._dir, "*%s" % self.cache_suffix)
]
@classmethod
def check(cls, cache, paths, name, alias_name='default'):
cache_path = pathlib.Path(cache._dir).resolve()
if any(path == cache_path for path in paths):
relation = "matches"
elif any(path in cache_path.parents for path in paths):
relation = "is inside"
elif any(cache_path in path.parents for path in paths):
relation = "contains"
else:
return None
return Warning(
f"Your '{alias_name}' cache configuration might expose your cache "
f"or lead to corruption of your data because its LOCATION "
f"{relation} {name}.", id="caches.W002",
)

View File

@ -1,4 +1,5 @@
import pathlib
import json
from django.conf import settings
from django.core.cache import DEFAULT_CACHE_ALIAS, caches
@ -21,6 +22,16 @@ def check_default_cache_is_configured(app_configs, **kwargs):
@register(Tags.caches, deploy=True)
def check_cache_location_not_exposed(app_configs, **kwargs):
cache = None
alias_name = ''
for alias, config in settings.CACHES.items():
if config.get('BACKEND').endswith("FileBasedCache"):
cache = caches[alias]
alias_name = alias
if cache is None:
return []
errors = []
for name in ("MEDIA_ROOT", "STATIC_ROOT", "STATICFILES_DIRS"):
setting = getattr(settings, name, None)
@ -34,43 +45,27 @@ def check_cache_location_not_exposed(app_configs, **kwargs):
paths.add(pathlib.Path(staticfiles_dir).resolve())
else:
paths = {pathlib.Path(setting).resolve()}
for alias in settings.CACHES:
cache = caches[alias]
if not isinstance(cache, FileBasedCache):
continue
cache_path = pathlib.Path(cache._dir).resolve()
if any(path == cache_path for path in paths):
relation = "matches"
elif any(path in cache_path.parents for path in paths):
relation = "is inside"
elif any(cache_path in path.parents for path in paths):
relation = "contains"
else:
continue
errors.append(
Warning(
f"Your '{alias}' cache configuration might expose your cache "
f"or lead to corruption of your data because its LOCATION "
f"{relation} {name}.",
id="caches.W002",
)
)
check_result = FileBasedCache.check(cache, paths, name, alias_name)
errors.append(check_result) if check_result else []
return errors
@register(Tags.caches)
def check_file_based_cache_is_absolute(app_configs, **kwargs):
errors = []
alias_name = None
location = None
for alias, config in settings.CACHES.items():
cache = caches[alias]
if not isinstance(cache, FileBasedCache):
continue
if not pathlib.Path(config["LOCATION"]).is_absolute():
errors.append(
Warning(
f"Your '{alias}' cache LOCATION path is relative. Use an "
f"absolute path instead.",
id="caches.W003",
)
if config.get('BACKEND').endswith("FileBasedCache"):
alias_name = alias
location = config
if alias_name is not None and not pathlib.Path(location.get("LOCATION")).is_absolute():
return Warning(
f"Your '{alias_name}' cache LOCATION path is relative. Use an "
f"absolute path instead.",
id="caches.W003",
)
return errors
return []