feat: add support for tuples to the marshaller (#267)

This commit is contained in:
J. Nick Koston 2023-11-10 08:46:37 -06:00 committed by GitHub
parent 6b48423b23
commit 0ccb7c5d87
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 44 additions and 8 deletions

View File

@ -72,7 +72,7 @@ cdef class Marshaller:
written=cython.uint,
i=cython.uint,
)
cdef unsigned int _write_struct(self, cython.list array, SignatureType type_)
cdef unsigned int _write_struct(self, object array, SignatureType type_)
cpdef write_variant(self, Variant variant, SignatureType type_)

View File

@ -136,10 +136,14 @@ class Marshaller:
return written + array_len
def write_struct(self, array: List[Any], type_: SignatureType) -> int:
def write_struct(
self, array: Union[Tuple[Any], List[Any]], type_: SignatureType
) -> int:
return self._write_struct(array, type_)
def _write_struct(self, array: List[Any], type_: SignatureType) -> int:
def _write_struct(
self, array: Union[Tuple[Any], List[Any]], type_: SignatureType
) -> int:
written = self._align(8)
for i, value in enumerate(array):
written += self._write_single(type_.children[i], value)

View File

@ -516,9 +516,10 @@ class ServiceInterface:
if out_len == 1:
result = [result]
else:
if type(result) is not list:
result_type = type(result)
if result_type is not list and result_type is not tuple:
raise SignatureBodyMismatchError(
"Expected signal to return a list of arguments"
"Expected signal to return a list or tuple of arguments"
)
if out_len != len(result):

View File

@ -258,10 +258,9 @@ class SignatureType:
child_type.verify(member)
def _verify_struct(self, body: Any) -> None:
# TODO allow tuples
if not isinstance(body, list):
if not isinstance(body, (list, tuple)):
raise SignatureBodyMismatchError(
f'DBus STRUCT type "(" must be Python type "list", got {type(body)}'
f'DBus STRUCT type "(" must be Python type "list" or "tuple", got {type(body)}'
)
if len(body) != len(self.children):

View File

@ -714,3 +714,29 @@ def test_unmarshall_multi_byte_string():
assert unmarshaller.message.signature == "as"
unpacked = unpack_variants(message.body)
assert unpacked == [["//doesntmatter/über"]]
def test_marshalling_struct_accepts_tuples():
"""Test marshalling a struct accepts tuples."""
msg = Message(
path="/test",
member="test",
signature="(s)",
body=[(RaucState.GOOD,)],
)
marshalled = msg._marshall(False)
unmarshalled_msg = Unmarshaller(io.BytesIO(marshalled)).unmarshall()
assert unpack_variants(unmarshalled_msg.body)[0] == [RaucState.GOOD.value]
def test_marshalling_struct_accepts_lists():
"""Test marshalling a struct accepts lists."""
msg = Message(
path="/test",
member="test",
signature="(s)",
body=[[RaucState.GOOD]],
)
marshalled = msg._marshall(False)
unmarshalled_msg = Unmarshaller(io.BytesIO(marshalled)).unmarshall()
assert unpack_variants(unmarshalled_msg.body)[0] == [RaucState.GOOD.value]

View File

@ -231,3 +231,9 @@ def test_variant_signature_type():
with pytest.raises(SignatureBodyMismatchError):
Variant(tree.types[0], "wrong")
def test_struct_accepts_tuples_or_lists():
tree = SignatureTree("(s)")
tree.verify([("ok",)])
tree.verify([["ok"]])