1 2
import inspect
2 2
from functools import wraps
3

4 2
from dynaconf.utils import recursively_evaluate_lazy_format
5 2
from dynaconf.utils import upperfy
6 2
from dynaconf.vendor.box import Box
7

8

9 2
def evaluate_lazy_format(f):
10
    """Marks a method on Dynabox instance to
11
    lazily evaluate LazyFormat objects upon access."""
12

13 2
    @wraps(f)
14
    def evaluate(dynabox, item, *args, **kwargs):
15 2
        value = f(dynabox, item, *args, **kwargs)
16 2
        settings = dynabox._box_config["box_settings"]
17

18 2
        if getattr(value, "_dynaconf_lazy_format", None):
19 2
            dynabox._box_config[
20
                f"raw_{item.lower()}"
21
            ] = f"@{value.formatter.token} {value.value}"
22

23 2
        return recursively_evaluate_lazy_format(value, settings)
24

25 2
    return evaluate
26

27

28 2
class DynaBox(Box):
29
    """Specialized Box for dynaconf
30
    it allows items/attrs to be found both in upper or lower case"""
31

32 2
    @evaluate_lazy_format
33
    def __getattr__(self, item, *args, **kwargs):
34 2
        try:
35 2
            return super(DynaBox, self).__getattr__(item, *args, **kwargs)
36 2
        except (AttributeError, KeyError):
37 2
            n_item = item.lower() if item.isupper() else upperfy(item)
38 2
            return super(DynaBox, self).__getattr__(n_item, *args, **kwargs)
39

40 2
    @evaluate_lazy_format
41
    def __getitem__(self, item, *args, **kwargs):
42 2
        try:
43 2
            return super(DynaBox, self).__getitem__(item, *args, **kwargs)
44 2
        except (AttributeError, KeyError):
45 2
            n_item = item.lower() if item.isupper() else upperfy(item)
46 2
            return super(DynaBox, self).__getitem__(n_item, *args, **kwargs)
47

48 2
    def __copy__(self):
49 2
        return self.__class__(
50
            super(Box, self).copy(),
51
            box_settings=self._box_config.get("box_settings"),
52
        )
53

54 2
    def copy(self):
55 2
        return self.__class__(
56
            super(Box, self).copy(),
57
            box_settings=self._box_config.get("box_settings"),
58
        )
59

60 2
    @evaluate_lazy_format
61 2
    def get(self, item, default=None, *args, **kwargs):
62 2
        if item not in self:  # toggle case
63 2
            item = item.lower() if item.isupper() else upperfy(item)
64 2
        return super(DynaBox, self).get(item, default, *args, **kwargs)
65

66 2
    def __dir__(self):
67 2
        keys = list(self.keys())
68 2
        reserved = [
69
            item[0]
70
            for item in inspect.getmembers(DynaBox)
71
            if not item[0].startswith("__")
72
        ]
73 2
        return (
74
            keys
75
            + [k.lower() for k in keys]
76
            + [k.upper() for k in keys]
77
            + reserved
78
        )

Read our documentation on viewing source code .

Loading