Skip to content

Commit

Permalink
Refactor ExtendedData closes #245
Browse files Browse the repository at this point in the history
  • Loading branch information
cleder committed Oct 30, 2023
1 parent 4c7588e commit b95b3c8
Show file tree
Hide file tree
Showing 2 changed files with 69 additions and 104 deletions.
163 changes: 63 additions & 100 deletions fastkml/data.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@
from typing import Optional
from typing import Tuple
from typing import Union
from typing import cast

import fastkml.config as config
from fastkml.base import _BaseObject
Expand All @@ -41,12 +40,6 @@
"ExtendedData",
"Schema",
"SchemaData",
"SchemaDataDictInput",
"SchemaDataInput",
"SchemaDataListInput",
"SchemaDataOutput",
"SchemaDataTupleInput",
"SchemaDataType",
"SimpleField",
]

Expand Down Expand Up @@ -132,17 +125,6 @@ def append(self, field: SimpleField) -> None:
"""Append a field."""
self._simple_fields.append(field)

def from_element(self, element: Element) -> None:
super().from_element(element)
self.name = element.get("name")
simple_fields = element.findall(f"{self.ns}SimpleField")
for simple_field in simple_fields:
sf_name = simple_field.get("name")
sf_type = simple_field.get("type")
display_name = simple_field.find(f"{self.ns}displayName")
sf_display_name = display_name.text if display_name is not None else None
self.append(SimpleField(sf_name, DataType(sf_type), sf_display_name))

def etree_element(
self,
precision: Optional[int] = None,
Expand Down Expand Up @@ -177,13 +159,10 @@ def get_display_name(field: Element) -> Optional[str]:
return display_name.text if display_name is not None else None

return [
cast(
SimpleField,
SimpleField(
name=field.get("name"),
type=DataType(field.get("type")),
display_name=get_display_name(field),
),
SimpleField(
name=field.get("name"),
type=DataType(field.get("type")),
display_name=get_display_name(field),
)
for field in element.findall(f"{ns}SimpleField")
if field is not None
Expand Down Expand Up @@ -249,16 +228,6 @@ def etree_element(
display_name.text = self.display_name
return element

def from_element(self, element: Element) -> None:
super().from_element(element)
self.name = element.get("name")
tmp_value = element.find(f"{self.ns}value")
if tmp_value is not None:
self.value = tmp_value.text
display_name = element.find(f"{self.ns}displayName")
if display_name is not None:
self.display_name = display_name.text

@classmethod
def _get_kwargs(
cls,
Expand All @@ -278,63 +247,6 @@ def _get_kwargs(
return kwargs


class ExtendedData(_XMLObject):
"""Represents a list of untyped name/value pairs. See docs:
-> 'Adding Untyped Name/Value Pairs'
https://developers.google.com/kml/documentation/extendeddata
"""

__name__ = "ExtendedData"

def __init__(
self,
ns: Optional[str] = None,
elements: Optional[List[Union[Data, "SchemaData"]]] = None,
) -> None:
super().__init__(ns)
self.elements = elements or []

def etree_element(
self,
precision: Optional[int] = None,
verbosity: Verbosity = Verbosity.normal,
) -> Element:
element = super().etree_element(precision=precision, verbosity=verbosity)
for subelement in self.elements:
element.append(subelement.etree_element())
return element

def from_element(self, element: Element) -> None:
super().from_element(element)
self.elements = []
untyped_data = element.findall(f"{self.ns}Data")
for ud in untyped_data:
el_data = Data(self.ns)
el_data.from_element(ud)
self.elements.append(el_data)
typed_data = element.findall(f"{self.ns}SchemaData")
for sd in typed_data:
el_schema_data = SchemaData(self.ns, "dummy")
el_schema_data.from_element(sd)
self.elements.append(el_schema_data)


SchemaDataType = List[Dict[str, Union[int, str]]]
SchemaDataListInput = List[Union[Dict[str, str], SchemaDataType]]
SchemaDataTupleInput = Tuple[Union[Dict[str, str], Tuple[Dict[str, Union[int, str]]]]]
SchemaDataDictInput = Dict[str, Union[int, str]]
SchemaDataInput = Optional[
Union[
SchemaDataListInput,
SchemaDataTupleInput,
SchemaDataDictInput,
]
]
SchemaDataOutput = Tuple[Dict[str, Union[int, str]], ...]


@dataclass(frozen=True)
class SimpleData:
name: str
Expand Down Expand Up @@ -402,14 +314,6 @@ def etree_element(
sd.text = data.value
return element

def from_element(self, element: Element) -> None:
super().from_element(element)
self.data = [] # type: ignore[assignment]
self.schema_url = element.get("schemaUrl")
simple_data = element.findall(f"{self.ns}SimpleData")
for sd in simple_data:
self.append_data(SimpleData(name=sd.get("name"), value=sd.text))

@classmethod
def _get_kwargs(
cls,
Expand All @@ -426,3 +330,62 @@ def _get_kwargs(
if sd is not None
]
return kwargs


class ExtendedData(_XMLObject):
"""Represents a list of untyped name/value pairs. See docs:
-> 'Adding Untyped Name/Value Pairs'
https://developers.google.com/kml/documentation/extendeddata
"""

__name__ = "ExtendedData"

def __init__(
self,
ns: Optional[str] = None,
elements: Optional[Iterable[Union[Data, SchemaData]]] = None,
) -> None:
super().__init__(ns)
self.elements = elements or []

def __repr__(self) -> str:
return (

Check warning on line 354 in fastkml/data.py

View check run for this annotation

Codecov / codecov/patch

fastkml/data.py#L354

Added line #L354 was not covered by tests
f"{self.__class__.__name__}("
f"ns='{self.ns}',"
f"elements='{self.elements}')"
)

def etree_element(
self,
precision: Optional[int] = None,
verbosity: Verbosity = Verbosity.normal,
) -> Element:
element = super().etree_element(precision=precision, verbosity=verbosity)
for subelement in self.elements:
element.append(subelement.etree_element())
return element

@classmethod
def _get_kwargs(
cls,
*,
ns: str,
element: Element,
strict: bool,
) -> Dict[str, Any]:
kwargs = super()._get_kwargs(ns=ns, element=element, strict=strict)
elements = []
untyped_data = element.findall(f"{ns}Data")
for ud in untyped_data:
el_data = Data.class_from_element(ns=ns, element=ud, strict=strict)
elements.append(el_data)
typed_data = element.findall(f"{ns}SchemaData")
for sd in typed_data:
el_schema_data = SchemaData.class_from_element(
ns=ns, element=sd, strict=strict
)
elements.append(el_schema_data)
kwargs["elements"] = elements
return kwargs
10 changes: 6 additions & 4 deletions fastkml/kml.py
Original file line number Diff line number Diff line change
Expand Up @@ -408,7 +408,7 @@ def etree_element(
phone_number.text = self._phone_number
return element

def from_element(self, element: Element) -> None:
def from_element(self, element: Element, strict: bool = False) -> None:
super().from_element(element)
name = element.find(f"{self.ns}name")
if name is not None:
Expand Down Expand Up @@ -465,9 +465,11 @@ def from_element(self, element: Element) -> None:
self._atom_author = s
extended_data = element.find(f"{self.ns}ExtendedData")
if extended_data is not None:
x = ExtendedData(self.ns)
x.from_element(extended_data)
self.extended_data = x
self.extended_data = ExtendedData.class_from_element(
ns=self.ns,
element=extended_data,
strict=strict,
)
address = element.find(f"{self.ns}address")
if address is not None:
self.address = address.text
Expand Down

0 comments on commit b95b3c8

Please sign in to comment.