summaryrefslogtreecommitdiff
path: root/lib/sqlalchemy/util
diff options
context:
space:
mode:
Diffstat (limited to 'lib/sqlalchemy/util')
-rw-r--r--lib/sqlalchemy/util/__init__.py7
-rw-r--r--lib/sqlalchemy/util/_collections.py10
-rw-r--r--lib/sqlalchemy/util/_py_collections.py28
-rw-r--r--lib/sqlalchemy/util/langhelpers.py7
4 files changed, 35 insertions, 17 deletions
diff --git a/lib/sqlalchemy/util/__init__.py b/lib/sqlalchemy/util/__init__.py
index 7e616cd74..406c8af24 100644
--- a/lib/sqlalchemy/util/__init__.py
+++ b/lib/sqlalchemy/util/__init__.py
@@ -21,9 +21,7 @@ from ._collections import flatten_iterator as flatten_iterator
from ._collections import has_dupes as has_dupes
from ._collections import has_intersection as has_intersection
from ._collections import IdentitySet as IdentitySet
-from ._collections import ImmutableContainer as ImmutableContainer
from ._collections import immutabledict as immutabledict
-from ._collections import ImmutableProperties as ImmutableProperties
from ._collections import LRUCache as LRUCache
from ._collections import merge_lists_w_ordering as merge_lists_w_ordering
from ._collections import ordered_column_set as ordered_column_set
@@ -33,6 +31,8 @@ from ._collections import OrderedProperties as OrderedProperties
from ._collections import OrderedSet as OrderedSet
from ._collections import PopulateDict as PopulateDict
from ._collections import Properties as Properties
+from ._collections import ReadOnlyContainer as ReadOnlyContainer
+from ._collections import ReadOnlyProperties as ReadOnlyProperties
from ._collections import ScopedRegistry as ScopedRegistry
from ._collections import sort_dictionary as sort_dictionary
from ._collections import ThreadLocalRegistry as ThreadLocalRegistry
@@ -107,6 +107,9 @@ from .langhelpers import get_func_kwargs as get_func_kwargs
from .langhelpers import getargspec_init as getargspec_init
from .langhelpers import has_compiled_ext as has_compiled_ext
from .langhelpers import HasMemoized as HasMemoized
+from .langhelpers import (
+ HasMemoized_ro_memoized_attribute as HasMemoized_ro_memoized_attribute,
+)
from .langhelpers import hybridmethod as hybridmethod
from .langhelpers import hybridproperty as hybridproperty
from .langhelpers import inject_docstring_text as inject_docstring_text
diff --git a/lib/sqlalchemy/util/_collections.py b/lib/sqlalchemy/util/_collections.py
index 2d974b737..bd73bf714 100644
--- a/lib/sqlalchemy/util/_collections.py
+++ b/lib/sqlalchemy/util/_collections.py
@@ -38,13 +38,13 @@ from .typing import Protocol
if typing.TYPE_CHECKING or not HAS_CYEXTENSION:
from ._py_collections import immutabledict as immutabledict
from ._py_collections import IdentitySet as IdentitySet
- from ._py_collections import ImmutableContainer as ImmutableContainer
+ from ._py_collections import ReadOnlyContainer as ReadOnlyContainer
from ._py_collections import ImmutableDictBase as ImmutableDictBase
from ._py_collections import OrderedSet as OrderedSet
from ._py_collections import unique_list as unique_list
else:
from sqlalchemy.cyextension.immutabledict import (
- ImmutableContainer as ImmutableContainer,
+ ReadOnlyContainer as ReadOnlyContainer,
)
from sqlalchemy.cyextension.immutabledict import (
ImmutableDictBase as ImmutableDictBase,
@@ -213,10 +213,10 @@ class Properties(Generic[_T]):
def __contains__(self, key: str) -> bool:
return key in self._data
- def as_immutable(self) -> "ImmutableProperties[_T]":
+ def as_readonly(self) -> "ReadOnlyProperties[_T]":
"""Return an immutable proxy for this :class:`.Properties`."""
- return ImmutableProperties(self._data)
+ return ReadOnlyProperties(self._data)
def update(self, value):
self._data.update(value)
@@ -263,7 +263,7 @@ class OrderedProperties(Properties[_T]):
Properties.__init__(self, OrderedDict())
-class ImmutableProperties(ImmutableContainer, Properties[_T]):
+class ReadOnlyProperties(ReadOnlyContainer, Properties[_T]):
"""Provide immutable dict/object attribute to an underlying dictionary."""
__slots__ = ()
diff --git a/lib/sqlalchemy/util/_py_collections.py b/lib/sqlalchemy/util/_py_collections.py
index d50352930..1016871aa 100644
--- a/lib/sqlalchemy/util/_py_collections.py
+++ b/lib/sqlalchemy/util/_py_collections.py
@@ -29,37 +29,45 @@ _KT = TypeVar("_KT", bound=Any)
_VT = TypeVar("_VT", bound=Any)
-class ImmutableContainer:
+class ReadOnlyContainer:
__slots__ = ()
+ def _readonly(self, *arg: Any, **kw: Any) -> NoReturn:
+ raise TypeError(
+ "%s object is immutable and/or readonly" % self.__class__.__name__
+ )
+
def _immutable(self, *arg: Any, **kw: Any) -> NoReturn:
raise TypeError("%s object is immutable" % self.__class__.__name__)
def __delitem__(self, key: Any) -> NoReturn:
- self._immutable()
+ self._readonly()
def __setitem__(self, key: Any, value: Any) -> NoReturn:
- self._immutable()
+ self._readonly()
def __setattr__(self, key: str, value: Any) -> NoReturn:
- self._immutable()
+ self._readonly()
-class ImmutableDictBase(ImmutableContainer, Dict[_KT, _VT]):
- def clear(self) -> NoReturn:
+class ImmutableDictBase(ReadOnlyContainer, Dict[_KT, _VT]):
+ def _readonly(self, *arg: Any, **kw: Any) -> NoReturn:
self._immutable()
+ def clear(self) -> NoReturn:
+ self._readonly()
+
def pop(self, key: Any, default: Optional[Any] = None) -> NoReturn:
- self._immutable()
+ self._readonly()
def popitem(self) -> NoReturn:
- self._immutable()
+ self._readonly()
def setdefault(self, key: Any, default: Optional[Any] = None) -> NoReturn:
- self._immutable()
+ self._readonly()
def update(self, *arg: Any, **kw: Any) -> NoReturn:
- self._immutable()
+ self._readonly()
class immutabledict(ImmutableDictBase[_KT, _VT]):
diff --git a/lib/sqlalchemy/util/langhelpers.py b/lib/sqlalchemy/util/langhelpers.py
index 8cf50c724..9e1194e23 100644
--- a/lib/sqlalchemy/util/langhelpers.py
+++ b/lib/sqlalchemy/util/langhelpers.py
@@ -1248,6 +1248,7 @@ if TYPE_CHECKING:
# of a property, meaning assignment needs to be disallowed
ro_memoized_property = property
ro_non_memoized_property = property
+
else:
memoized_property = ro_memoized_property = _memoized_property
non_memoized_property = ro_non_memoized_property = _non_memoized_property
@@ -1348,6 +1349,12 @@ class HasMemoized:
return update_wrapper(oneshot, fn)
+if TYPE_CHECKING:
+ HasMemoized_ro_memoized_attribute = property
+else:
+ HasMemoized_ro_memoized_attribute = HasMemoized.memoized_attribute
+
+
class MemoizedSlots:
"""Apply memoized items to an object using a __getattr__ scheme.