FrozenConfiguration

class upsilonconf.FrozenConfiguration(**kwargs: Hashable | set | Sequence | Mapping)[source]

Immutable configuration.

FrozenConfiguration is an immutable ConfigurationBase implementation. This means that values can not be added, changed and/or deleted. As a result, FrozenConfiguration is a Hashable type, which means that they can be used in a set or serve as keys in a dict.

Added in version 0.7.0.

Changed in version 0.8.0: set objects are now stored as frozenset istead of tuple.

Warning

In the current implementation, using method names as keys is possible,

>>> conf = FrozenConfiguration()
>>> print(conf.items)
<bound method ConfigurationBase.items of FrozenConfiguration()>
>>> conf = FrozenConfiguration(items=123)
>>> print(conf.items)
123

but it can lead to some unexpected behaviour.

>>> print(conf)
{items: 123}
>>> conf == {"items": 123}
Traceback (most recent call last):
    ...
TypeError: 'int' object is not callable

See also

ConfigurationBase

the configuration interface.

PlainConfiguration

a mutable configuration.

Examples

Starting with a simple configuration.

>>> conf = FrozenConfiguration(foo=0, bar="bar", baz={'a': 1, 'b': 2})
>>> print(conf)
{foo: 0, bar: bar, baz: {a: 1, b: 2}}

Attempts to change the configuration will result in errors.

>>> conf.surprise = None
Traceback (most recent call last):
    ...
AttributeError: 'FrozenConfiguration' object has no attribute 'surprise'
>>> conf["surprise"] = []
Traceback (most recent call last):
    ...
TypeError: 'FrozenConfiguration' object does not support item assignment
>>> del conf.baz.a
Traceback (most recent call last):
    ...
AttributeError: 'FrozenConfiguration' object attribute 'a' is read-only

Values should be of hashable types, but non-hashable types are converted if possible.

>>> print(FrozenConfiguration(value=[1, 2, 3]))
{value: (1, 2, 3)}
>>> class Unhashable:
...     def __eq__(self, other):
...         return False
...
>>> print(FrozenConfiguration(value=Unhashable()))
Traceback (most recent call last):
    ...
TypeError: unhashable type: 'Unhashable'

Frozen configurations can be used keys in a dict.

>>> results = {
...     FrozenConfiguration(option=1): 0.1,
...     FrozenConfiguration(option=2): 0.9,
... }
>>> print(max(results.items(), key=lambda kv: kv[1]))
(FrozenConfiguration(option=2), 0.9)