Skip to content
Snippets Groups Projects
Commit c5f93108 authored by Piotr Maślanka's avatar Piotr Maślanka
Browse files

v2.2.7

parent 68199070
No related branches found
No related tags found
No related merge requests found
# v2.2.7
* _TBA_
* added inheritance from `abc` to Immutable
# v2.2.6
......
......@@ -63,11 +63,13 @@ Immutable
=========
Make your classes immutable. Normal assignment is only supported in the constructor,
anywhere else it's a TypeError
anywhere else it's a TypeError.
Immutable inherits from abc.ABCMeta, so it's safe to use abstract base classes here.
::
class Test(Immutable):
class Test(Immutable, metaclass=ABCMeta):
attr: str = None
......
# coding=UTF-8
__version__ = '2.2.7a1'
__version__ = '2.2.7'
from abc import ABCMeta
__all__ = ['Immutable']
class ImmutableMetaType(type):
class ImmutableMetaType(ABCMeta):
def __call__(cls, *args, **kwargs):
p = type.__call__(cls, *args, **kwargs)
p.__class__ = LockedImmutable
p.__dict__['_Immutable__locked_for_writes'] = True
return p
......@@ -19,14 +21,17 @@ class Immutable(metaclass=ImmutableMetaType):
>>> self.attribute = 'value'
"""
class LockedImmutable(Immutable):
__doc__ = Immutable.__doc__
__locked_for_writes: bool = False
# Following make this class immutable
def __setattr__(self, attr, value):
raise TypeError('%s does not support attribute assignment' % (self.__class__.__qualname__,))
if self.__locked_for_writes:
raise TypeError('%s does not support attribute assignment' % (self.__class__.__qualname__,))
else:
super().__setattr__(attr, value)
def __delattr__(self, attr):
raise TypeError('%s does not support attribute deletion' % (self.__class__.__qualname__,))
if self.__locked_for_writes:
raise TypeError('%s does not support attribute deletion' % (self.__class__.__qualname__,))
else:
super().__delattr__(attr)
import copy
import abc
import unittest
import mock
......@@ -152,13 +153,7 @@ class TestHeap(unittest.TestCase):
class TestImmutable(unittest.TestCase):
def test_immutable(self):
class Point2D(Immutable):
def __init__(self, x: float, y: float):
self.x = x
self.y = y
a = Point2D(2.5, 2)
def _test_an_instance(self, a):
self.assertEqual(a.x, 2.5)
self.assertEqual(a.y, 2)
......@@ -171,3 +166,30 @@ class TestImmutable(unittest.TestCase):
del a.x
self.assertRaises(TypeError, delete_x)
def test_immutable(self):
class Point2D(Immutable):
def __init__(self, x: float, y: float):
self.x = x
self.y = y
self._test_an_instance(Point2D(2.5, 2))
def test_immutable_abc(self):
class Point2D(abc.ABC, Immutable):
def __init__(self, x: float, y: float):
self.x = x
self.y = y
self._test_an_instance(Point2D(2.5, 2))
def test_advanced_inheritance_hierarchy(self):
class BaseClass(abc.ABC):
pass
class Point2D(BaseClass, Immutable):
def __init__(self, x: float, y: float):
self.x = x
self.y = y
self._test_an_instance(Point2D(2.5, 2))
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment