cultcache-py: the record decode applies a slot default in one place; plain field helper, SlotCodec and field immutability pinned
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
ff1138ca4c
commit
eae7207df5
2 changed files with 19 additions and 3 deletions
|
|
@ -398,12 +398,12 @@ def _record_codec(type: str, normalized: list[DatabaseEntryField], cls: type[Any
|
|||
for field in normalized:
|
||||
if field.key < len(raw):
|
||||
value = decode_slot(field, raw[field.key])
|
||||
elif field.default is not MISSING:
|
||||
value = field.default() if callable(field.default) else field.default
|
||||
else:
|
||||
elif field.default is MISSING:
|
||||
raise ValueError(
|
||||
f"DatabaseEntry document type {type!r} is missing required slot {field.key}"
|
||||
)
|
||||
else:
|
||||
value = None
|
||||
if value is None and field.default is not MISSING:
|
||||
value = field.default() if callable(field.default) else field.default
|
||||
values[field.name] = value
|
||||
|
|
|
|||
|
|
@ -353,6 +353,22 @@ class RecordCodecTests(unittest.TestCase):
|
|||
define_record_codec("Nothing", [])
|
||||
self.assertEqual(str(empty.exception), "DatabaseEntry document types require at least one field")
|
||||
|
||||
def test_a_plain_field_helper_makes_a_required_slot_with_no_codec(self) -> None:
|
||||
plain = define_record_codec("Plain", [database_entry_field("id", 0), database_entry_field("label", 1)])
|
||||
self.assertEqual(plain.decode(plain.encode({"id": "a", "label": "b"})), {"id": "a", "label": "b"})
|
||||
with self.assertRaises(ValueError) as caught:
|
||||
plain.decode(["a"])
|
||||
self.assertEqual(str(caught.exception), "DatabaseEntry document type 'Plain' is missing required slot 1")
|
||||
field = database_entry_field("id", 0)
|
||||
self.assertIsNone(field.codec)
|
||||
self.assertFalse(field.many)
|
||||
|
||||
def test_slot_codecs_and_fields_are_immutable(self) -> None:
|
||||
with self.assertRaises(dataclasses.FrozenInstanceError):
|
||||
node.encode = None # type: ignore[misc]
|
||||
with self.assertRaises(dataclasses.FrozenInstanceError):
|
||||
database_entry_field("id", 0).key = 1 # type: ignore[misc]
|
||||
|
||||
def test_a_negative_slot_key_is_refused_but_zero_is_not(self) -> None:
|
||||
database_entry_field("zero", 0)
|
||||
with self.assertRaises(ValueError) as caught:
|
||||
|
|
|
|||
Loading…
Reference in a new issue