mirror of
https://github.com/tiqi-group/pydase.git
synced 2025-04-20 00:10:03 +02:00
updates generate_serialized_data_paths to handle dictionaries well
This commit is contained in:
parent
1c1584c2cf
commit
b9131c9df2
@ -468,50 +468,82 @@ def get_container_item_by_key(
|
|||||||
raise SerializationPathError(f"Key '{processed_key}': {e}")
|
raise SerializationPathError(f"Key '{processed_key}': {e}")
|
||||||
|
|
||||||
|
|
||||||
def generate_serialized_data_paths(
|
def get_data_paths_from_serialized_object( # noqa: C901
|
||||||
data: dict[str, Any], parent_path: str = ""
|
serialized_obj: SerializedObject,
|
||||||
|
parent_path: str = "",
|
||||||
) -> list[str]:
|
) -> list[str]:
|
||||||
"""
|
"""
|
||||||
Generate a list of access paths for all attributes in a dictionary representing
|
Recursively extracts full access paths from a serialized object.
|
||||||
data serialized with `pydase.utils.serializer.Serializer`, excluding those that are
|
|
||||||
methods. This function handles nested structures, including lists, by generating
|
|
||||||
paths for each element in the nested lists.
|
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
data (dict[str, Any]): The dictionary representing serialized data, typically
|
serialized_obj (SerializedObject):
|
||||||
produced by `pydase.utils.serializer.Serializer`.
|
The dictionary representing the serialization of an object. Produced by
|
||||||
parent_path (str, optional): The base path to prepend to the keys in the `data`
|
`pydase.utils.serializer.Serializer`.
|
||||||
dictionary to form the access paths. Defaults to an empty string.
|
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
list[str]: A list of strings where each string is a dot-notation access path
|
list[str]:
|
||||||
to an attribute in the serialized data. For list elements, the path includes
|
A list of strings, each representing a full access path in the serialized
|
||||||
the index in square brackets.
|
object.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
paths: list[str] = []
|
paths: list[str] = []
|
||||||
for key, value in data.items():
|
|
||||||
new_path = f"{parent_path}.{key}" if parent_path else key
|
if isinstance(serialized_obj["value"], list):
|
||||||
|
for index, value in enumerate(serialized_obj["value"]):
|
||||||
|
new_path = f"{parent_path}[{index}]"
|
||||||
paths.append(new_path)
|
paths.append(new_path)
|
||||||
if serialized_dict_is_nested_object(value):
|
if serialized_dict_is_nested_object(value):
|
||||||
if isinstance(value["value"], list):
|
paths.extend(get_data_paths_from_serialized_object(value, new_path))
|
||||||
for index, item in enumerate(value["value"]):
|
|
||||||
indexed_key_path = f"{new_path}[{index}]"
|
elif serialized_dict_is_nested_object(serialized_obj):
|
||||||
paths.append(indexed_key_path)
|
for key, value in cast(
|
||||||
if serialized_dict_is_nested_object(item):
|
dict[str, SerializedObject], serialized_obj["value"]
|
||||||
paths.extend(
|
).items():
|
||||||
generate_serialized_data_paths(
|
# Serialized dictionaries need to have a different new_path than nested
|
||||||
item["value"], indexed_key_path
|
# classes
|
||||||
)
|
if serialized_obj["type"] == "dict":
|
||||||
)
|
processed_key = key
|
||||||
continue
|
if isinstance(key, str):
|
||||||
# TODO: add dict?
|
processed_key = f'"{key}"'
|
||||||
paths.extend(generate_serialized_data_paths(value["value"], new_path))
|
new_path = f"{parent_path}[{processed_key}]"
|
||||||
|
else:
|
||||||
|
new_path = f"{parent_path}.{key}" if parent_path != "" else key
|
||||||
|
|
||||||
|
paths.append(new_path)
|
||||||
|
if serialized_dict_is_nested_object(value):
|
||||||
|
paths.extend(get_data_paths_from_serialized_object(value, new_path))
|
||||||
|
|
||||||
|
return paths
|
||||||
|
|
||||||
|
|
||||||
|
def generate_serialized_data_paths(
|
||||||
|
data: dict[str, SerializedObject],
|
||||||
|
) -> list[str]:
|
||||||
|
"""
|
||||||
|
Recursively extracts full access paths from a serialized DataService class instance.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
data (dict[str, SerializedObject]):
|
||||||
|
The value of the "value" key of a serialized DataService class instance.
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
list[str]:
|
||||||
|
A list of strings, each representing a full access path in the serialized
|
||||||
|
object.
|
||||||
|
"""
|
||||||
|
|
||||||
|
paths: list[str] = []
|
||||||
|
|
||||||
|
for key, value in data.items():
|
||||||
|
paths.append(key)
|
||||||
|
|
||||||
|
if serialized_dict_is_nested_object(value):
|
||||||
|
paths.extend(get_data_paths_from_serialized_object(value, key))
|
||||||
return paths
|
return paths
|
||||||
|
|
||||||
|
|
||||||
def serialized_dict_is_nested_object(serialized_dict: SerializedObject) -> bool:
|
def serialized_dict_is_nested_object(serialized_dict: SerializedObject) -> bool:
|
||||||
return (
|
value = serialized_dict["value"]
|
||||||
serialized_dict["type"] != "Quantity"
|
# We are excluding Quantity here as the value corresponding to the "value" key is
|
||||||
and isinstance(serialized_dict["value"], dict)
|
# a dictionary of the form {"magnitude": ..., "unit": ...}
|
||||||
) or isinstance(serialized_dict["value"], list)
|
return serialized_dict["type"] != "Quantity" and (isinstance(value, dict | list))
|
||||||
|
Loading…
x
Reference in New Issue
Block a user