From 6bb2f865158099f0460a68c342dbe6f695d0be8c Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 10:17:37 +0100 Subject: [PATCH 01/11] remove zeitspanne --- src/bo4e/com/zeitspanne.py | 33 --------------------------------- 1 file changed, 33 deletions(-) delete mode 100644 src/bo4e/com/zeitspanne.py diff --git a/src/bo4e/com/zeitspanne.py b/src/bo4e/com/zeitspanne.py deleted file mode 100644 index 73fc7b047..000000000 --- a/src/bo4e/com/zeitspanne.py +++ /dev/null @@ -1,33 +0,0 @@ -""" -contains the COM Zeitspanne -""" - -from typing import Optional - -import pydantic - -from bo4e.com.com import COM - -from ..utils import postprocess_docstring - - -@postprocess_docstring -class Zeitspanne(COM): - """ - Eine Zeitspanne ist definiert aus Start und/oder Ende. - Der Unterschied zur Menge (die auch zur Abbildung von Zeitmengen genutzt wird) ist, dass konkrete Start- und Endzeitpunkte angegeben werden. - Die Zeitspanne ist aus dem COM Zeitraum hervorgegangen, das in Zeitspanne und Menge aufgeteilt wurde. - - .. raw:: html - - - - .. HINT:: - `Zeitspanne JSON Schema `_ - - """ - - start: Optional[pydantic.AwareDatetime] = None - """inklusiver Beginn""" - ende: Optional[pydantic.AwareDatetime] = None - """exklusives Ende""" From 36f10c210f6418910be637b9860cea6c4da950f7 Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 10:36:09 +0100 Subject: [PATCH 02/11] delete test zeitspanne --- tests/test_zeitspanne.py | 21 --------------------- 1 file changed, 21 deletions(-) delete mode 100644 tests/test_zeitspanne.py diff --git a/tests/test_zeitspanne.py b/tests/test_zeitspanne.py deleted file mode 100644 index 51f9c9744..000000000 --- a/tests/test_zeitspanne.py +++ /dev/null @@ -1,21 +0,0 @@ -from datetime import datetime, timezone - -from bo4e.com.zeitspanne import Zeitspanne - - -class TestZeitspanne: - def test_zeitspanne(self) -> None: - """ - Test de-/serialisation of Zeitspanne - """ - zeitspanne = Zeitspanne( - start=datetime(2013, 5, 1, tzinfo=timezone.utc), ende=datetime(2022, 1, 28, tzinfo=timezone.utc) - ) - - json_string = zeitspanne.model_dump_json(by_alias=True) - - assert "2013-05-01T00:00:00Z" in json_string - assert "2022-01-28T00:00:00Z" in json_string - - zeitspanne_deserialized = Zeitspanne.model_validate_json(json_string) - assert zeitspanne_deserialized == zeitspanne From dc35783819ac1efc42f95ea74febb6febf4374d5 Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 10:38:14 +0100 Subject: [PATCH 03/11] fix com zeitraum --- src/bo4e/com/zeitraum.py | 20 +++++++++++--------- 1 file changed, 11 insertions(+), 9 deletions(-) diff --git a/src/bo4e/com/zeitraum.py b/src/bo4e/com/zeitraum.py index 90325ab44..0d0d4464a 100644 --- a/src/bo4e/com/zeitraum.py +++ b/src/bo4e/com/zeitraum.py @@ -3,11 +3,9 @@ and corresponding marshmallow schema for de-/serialization """ -from decimal import Decimal +from datetime import date, time from typing import TYPE_CHECKING, Optional -import pydantic - from ..utils import postprocess_docstring from .com import COM @@ -36,9 +34,13 @@ class Zeitraum(COM): """ - einheit: Optional["Mengeneinheit"] = None - dauer: Optional[Decimal] = None - startdatum: Optional[pydantic.AwareDatetime] = None - enddatum: Optional[pydantic.AwareDatetime] = None - startzeitpunkt: Optional[pydantic.AwareDatetime] = None - endzeitpunkt: Optional[pydantic.AwareDatetime] = None + startdatum: Optional[date] = None + """Startdatum, inklusiv""" + enddatum: Optional[date] = None + """Enddatum, inklusiv""" + startuhrzeit: Optional[time] = None + """Startuhrzeit, inklusiv mit Zeitzone""" + enduhrzeit: Optional[time] = None + """Enduhrzeit, exklusiv mit Zeitzone""" + dauer: Optional[str] = None + """Dauer""" From 0c4b16f29b7921974ba72a15eb788a7a6e1ea37e Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 10:38:35 +0100 Subject: [PATCH 04/11] add more test to test_zeitraum --- tests/test_zeitraum.py | 36 ++++++++++++++++++++++++++++++++---- 1 file changed, 32 insertions(+), 4 deletions(-) diff --git a/tests/test_zeitraum.py b/tests/test_zeitraum.py index 88f9c817e..a2ed5a8f1 100644 --- a/tests/test_zeitraum.py +++ b/tests/test_zeitraum.py @@ -1,8 +1,8 @@ -from decimal import Decimal +from datetime import date, time, timedelta, timezone import pytest -from bo4e import Mengeneinheit, Zeitraum +from bo4e import Zeitraum from tests.serialization_helper import assert_serialization_roundtrip @@ -12,9 +12,37 @@ class TestZeitraum: [ pytest.param( Zeitraum( - einheit=Mengeneinheit.TAG, - dauer=Decimal(21), + dauer="P1DT30H4S", ), + id="P1DT30H4S", + ), + pytest.param( + Zeitraum( + startdatum=date(2025, 1, 1), + enddatum=date(2025, 1, 31), + ), + id="startdatum-enddatum", + ), + pytest.param( + Zeitraum( + startuhrzeit=time(10, 0, 0), + enduhrzeit=time(11, 0, 0), + ), + id="startuhrzeit-enduhrzeit", + ), + pytest.param( + Zeitraum( + startuhrzeit=time(10, 0, 0, tzinfo=timezone.utc), + enduhrzeit=time(11, 0, 0, tzinfo=timezone.utc), + ), + id="startuhrzeit-enduhrzeit-utc-timezone", + ), + pytest.param( + Zeitraum( + startuhrzeit=time(18, 0, 0, tzinfo=timezone(timedelta(hours=1), "Europe/Berlin")), + enduhrzeit=time(19, 0, 0, tzinfo=timezone(timedelta(hours=1), "Europe/Berlin")), + ), + id="startuhrzeit-enduhrzeit-utc-timezone", ), ], ) From 7dbf196734b01414667a2e659377e319bf4322d0 Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 10:54:57 +0100 Subject: [PATCH 05/11] update all bos and coms with the new approach just COM Zeitraum --- src/bo4e/__init__.py | 2 -- src/bo4e/bo/lokationszuordnung.py | 6 +++--- src/bo4e/com/zeitreihenwert.py | 4 ++-- tests/test_lokationszuordnung.py | 5 ++--- tests/test_rechnung.py | 4 ++-- tests/test_regionalepreisgarantie.py | 8 +++++--- tests/test_vertragskonditionen.py | 6 +++--- tests/test_zeitreihenwert.py | 8 +++----- 8 files changed, 20 insertions(+), 23 deletions(-) diff --git a/src/bo4e/__init__.py b/src/bo4e/__init__.py index 255977773..c45aebf00 100644 --- a/src/bo4e/__init__.py +++ b/src/bo4e/__init__.py @@ -101,7 +101,6 @@ "Zaehlzeitregister", "Zeitraum", "Zeitreihenwert", - "Zeitspanne", "Zustaendigkeit", "AbgabeArt", "Angebotsstatus", @@ -295,7 +294,6 @@ from .com.zaehlzeitregister import Zaehlzeitregister from .com.zeitraum import Zeitraum from .com.zeitreihenwert import Zeitreihenwert -from .com.zeitspanne import Zeitspanne from .com.zustaendigkeit import Zustaendigkeit # Import Enums diff --git a/src/bo4e/bo/lokationszuordnung.py b/src/bo4e/bo/lokationszuordnung.py index 4e2c08065..7ee433b57 100644 --- a/src/bo4e/bo/lokationszuordnung.py +++ b/src/bo4e/bo/lokationszuordnung.py @@ -16,7 +16,7 @@ from ..bo.netzlokation import Netzlokation from ..bo.steuerbareressource import SteuerbareRessource from ..bo.technischeressource import TechnischeRessource - from ..com.zeitspanne import Zeitspanne + from ..com.zeitraum import Zeitraum @postprocess_docstring @@ -45,8 +45,8 @@ class Lokationszuordnung(Geschaeftsobjekt): """Liste mit referenzierten technischen Ressourcen""" steuerbare_ressourcen: Optional[list["SteuerbareRessource"]] = None """Liste mit referenzierten steuerbaren Ressourcen""" - gueltigkeit: Optional["Zeitspanne"] = None - """Zeitspanne der Gültigkeit""" + gueltigkeit: Optional["Zeitraum"] = None + """Zeitraum der Gültigkeit""" zuordnungstyp: Optional[str] = None """Verknüpfungsrichtung z.B. Malo-Melo [TODO: Eventuell anderer Datentyp]""" lokationsbuendelcode: Optional[str] = None diff --git a/src/bo4e/com/zeitreihenwert.py b/src/bo4e/com/zeitreihenwert.py index a4f6f9e91..3cb2e56cf 100644 --- a/src/bo4e/com/zeitreihenwert.py +++ b/src/bo4e/com/zeitreihenwert.py @@ -10,7 +10,7 @@ from .com import COM if TYPE_CHECKING: - from ..com.zeitspanne import Zeitspanne + from ..com.zeitraum import Zeitraum from ..enum.messwertstatus import Messwertstatus from ..enum.messwertstatuszusatz import Messwertstatuszusatz @@ -32,7 +32,7 @@ class Zeitreihenwert(COM): """ - zeitspanne: Optional["Zeitspanne"] = None + zeitspanne: Optional["Zeitraum"] = None # TODO: rename to zeitraum? """Zeitespanne für das Messintervall""" wert: Optional[Decimal] = None """Der in der Zeitspanne gültige Wert.""" diff --git a/tests/test_lokationszuordnung.py b/tests/test_lokationszuordnung.py index f16a7aad7..02a9c18fa 100644 --- a/tests/test_lokationszuordnung.py +++ b/tests/test_lokationszuordnung.py @@ -1,5 +1,4 @@ import pytest -from pydantic import AwareDatetime from bo4e import ( Lokationszuordnung, @@ -8,7 +7,7 @@ Netzlokation, SteuerbareRessource, TechnischeRessource, - Zeitspanne, + Zeitraum, ) from tests.serialization_helper import assert_serialization_roundtrip @@ -24,7 +23,7 @@ class TestLokationszuordnung: netzlokationen=[Netzlokation()], technische_ressourcen=[TechnischeRessource()], steuerbare_ressourcen=[SteuerbareRessource()], - gueltigkeit=Zeitspanne(), + gueltigkeit=Zeitraum(), zuordnungstyp="Zuordnungstyp", lokationsbuendelcode="9992 00000 125 6", ), diff --git a/tests/test_rechnung.py b/tests/test_rechnung.py index 9ad9cd9e9..fc9b0564e 100644 --- a/tests/test_rechnung.py +++ b/tests/test_rechnung.py @@ -40,7 +40,7 @@ class TestRechnung: faelligkeitsdatum=datetime.today().replace(tzinfo=timezone.utc), rechnungstyp=Rechnungstyp.ENDKUNDENRECHNUNG, original_rechnungsnummer="RE-2022-01-21_1701", - rechnungsperiode=Zeitraum(einheit=Mengeneinheit.TAG, dauer=Decimal(21)), + rechnungsperiode=Zeitraum(dauer="P21D"), rechnungsersteller=Geschaeftspartner(), rechnungsempfaenger=Geschaeftspartner(), gesamtnetto=Betrag(wert=Decimal(12.5), waehrung=Waehrungscode.EUR), @@ -91,7 +91,7 @@ class TestRechnung: faelligkeitsdatum=datetime.today().replace(tzinfo=timezone.utc), rechnungstyp=Rechnungstyp.ENDKUNDENRECHNUNG, original_rechnungsnummer="RE-2022-01-21_1701", - rechnungsperiode=Zeitraum(einheit=Mengeneinheit.TAG, dauer=Decimal(21)), + rechnungsperiode=Zeitraum(dauer="P21D"), rechnungsersteller=Geschaeftspartner(), rechnungsempfaenger=Geschaeftspartner(), gesamtnetto=Betrag(wert=Decimal(12.5), waehrung=Waehrungscode.EUR), diff --git a/tests/test_regionalepreisgarantie.py b/tests/test_regionalepreisgarantie.py index 6ac127c54..2344d2ec9 100644 --- a/tests/test_regionalepreisgarantie.py +++ b/tests/test_regionalepreisgarantie.py @@ -1,4 +1,4 @@ -from datetime import datetime, timezone +from datetime import datetime, time import pytest @@ -22,8 +22,10 @@ class TestRegionalePreisgarantie: RegionalePreisgarantie( preisgarantietyp=Preisgarantietyp.NUR_ENERGIEPREIS, zeitliche_gueltigkeit=Zeitraum( - startzeitpunkt=datetime(2011, 2, 5, 16, 43, tzinfo=timezone.utc), - endzeitpunkt=datetime(2021, 7, 30, tzinfo=timezone.utc), + startdatum=datetime(2011, 2, 5), + startuhrzeit=time(16, 43), + enddatum=datetime(2021, 7, 30), + enduhrzeit=time(16, 43), ), regionale_gueltigkeit=RegionaleGueltigkeit( gueltigkeitstyp=Gueltigkeitstyp.NUR_IN, diff --git a/tests/test_vertragskonditionen.py b/tests/test_vertragskonditionen.py index f21f391cc..c3904a5ff 100644 --- a/tests/test_vertragskonditionen.py +++ b/tests/test_vertragskonditionen.py @@ -19,9 +19,9 @@ class TestVertragskonditionen: startdatum=datetime(2012, 9, 21, tzinfo=timezone.utc), enddatum=datetime(2013, 10, 11, tzinfo=timezone.utc), ), - kuendigungsfrist=Zeitraum(einheit=Mengeneinheit.WOCHE, dauer=Decimal(3)), - vertragsverlaengerung=Zeitraum(einheit=Mengeneinheit.TAG, dauer=Decimal(14)), - abschlagszyklus=Zeitraum(einheit=Mengeneinheit.TAG, dauer=Decimal(5)), + kuendigungsfrist=Zeitraum(dauer="P3W"), + vertragsverlaengerung=Zeitraum(dauer="P14D"), + abschlagszyklus=Zeitraum(dauer="P5D"), ), ), pytest.param( diff --git a/tests/test_zeitreihenwert.py b/tests/test_zeitreihenwert.py index 924844181..cf7529e63 100644 --- a/tests/test_zeitreihenwert.py +++ b/tests/test_zeitreihenwert.py @@ -1,9 +1,9 @@ -from datetime import datetime, timezone +from datetime import datetime from decimal import Decimal import pytest -from bo4e import Messwertstatus, Messwertstatuszusatz, Zeitreihenwert, Zeitspanne +from bo4e import Messwertstatus, Messwertstatuszusatz, Zeitraum, Zeitreihenwert from tests.serialization_helper import assert_serialization_roundtrip @@ -13,9 +13,7 @@ class TestZeitreihenwert: [ pytest.param( Zeitreihenwert( - zeitspanne=Zeitspanne( - start=datetime(2013, 5, 1, tzinfo=timezone.utc), ende=datetime(2022, 1, 28, tzinfo=timezone.utc) - ), + zeitspanne=Zeitraum(startdatum=datetime(2013, 5, 1), enddatum=datetime(2022, 1, 28)), wert=Decimal(2.5), status=Messwertstatus.ABGELESEN, statuszusatz=Messwertstatuszusatz.Z78_GERAETEWECHSEL, From f54a078f0b081fb8f62aad9dd6bca48f5556ca32 Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 10:55:08 +0100 Subject: [PATCH 06/11] remove empty lines --- src/bo4e/com/zeitraum.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/bo4e/com/zeitraum.py b/src/bo4e/com/zeitraum.py index 0d0d4464a..badddaf5b 100644 --- a/src/bo4e/com/zeitraum.py +++ b/src/bo4e/com/zeitraum.py @@ -14,8 +14,6 @@ # pylint: disable=too-few-public-methods - - @postprocess_docstring class Zeitraum(COM): """ From d97917100faa36570e25c380fa28001d8e35db6c Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 10:55:29 +0100 Subject: [PATCH 07/11] improve naming of tests --- tests/test_zeitraum.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/test_zeitraum.py b/tests/test_zeitraum.py index a2ed5a8f1..7b6645231 100644 --- a/tests/test_zeitraum.py +++ b/tests/test_zeitraum.py @@ -14,7 +14,7 @@ class TestZeitraum: Zeitraum( dauer="P1DT30H4S", ), - id="P1DT30H4S", + id="period-P1DT30H4S", ), pytest.param( Zeitraum( @@ -42,7 +42,7 @@ class TestZeitraum: startuhrzeit=time(18, 0, 0, tzinfo=timezone(timedelta(hours=1), "Europe/Berlin")), enduhrzeit=time(19, 0, 0, tzinfo=timezone(timedelta(hours=1), "Europe/Berlin")), ), - id="startuhrzeit-enduhrzeit-utc-timezone", + id="startuhrzeit-enduhrzeit-berlin-timezone", ), ], ) From 0574551b366f0139c0e712647f57985e46defa01 Mon Sep 17 00:00:00 2001 From: kevin <68426071+hf-krechan@users.noreply.github.com> Date: Thu, 20 Mar 2025 11:03:28 +0100 Subject: [PATCH 08/11] improve docstring for `Dauer` Co-authored-by: Annika <73470827+hf-aschloegl@users.noreply.github.com> --- src/bo4e/com/zeitraum.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/bo4e/com/zeitraum.py b/src/bo4e/com/zeitraum.py index badddaf5b..3495c5157 100644 --- a/src/bo4e/com/zeitraum.py +++ b/src/bo4e/com/zeitraum.py @@ -41,4 +41,4 @@ class Zeitraum(COM): enduhrzeit: Optional[time] = None """Enduhrzeit, exklusiv mit Zeitzone""" dauer: Optional[str] = None - """Dauer""" + """Dauer in ISO 8601 , example: 'P1DT30H4S', siehe https://datatracker.ietf.org/doc/html/rfc3339 """ From 6c4c7a225cd0c3807aea2e51a7c3b598a0ac484e Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 11:04:08 +0100 Subject: [PATCH 09/11] replace property zeitspanne with zeitraum --- src/bo4e/com/zeitreihenwert.py | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/src/bo4e/com/zeitreihenwert.py b/src/bo4e/com/zeitreihenwert.py index 3cb2e56cf..989ecb86e 100644 --- a/src/bo4e/com/zeitreihenwert.py +++ b/src/bo4e/com/zeitreihenwert.py @@ -16,8 +16,6 @@ # pylint: disable=too-few-public-methods - - @postprocess_docstring class Zeitreihenwert(COM): """ @@ -32,12 +30,11 @@ class Zeitreihenwert(COM): """ - zeitspanne: Optional["Zeitraum"] = None # TODO: rename to zeitraum? - """Zeitespanne für das Messintervall""" + zeitraum: Optional["Zeitraum"] = None + """Zeitraum für das Messintervall""" wert: Optional[Decimal] = None - """Der in der Zeitspanne gültige Wert.""" + """Der in dem Zeitraum gültige Wert.""" status: Optional["Messwertstatus"] = None """Der Status gibt an, wie der Wert zu interpretieren ist, z.B. in Berechnungen.""" - statuszusatz: Optional["Messwertstatuszusatz"] = None """Eine Zusatzinformation zum Status, beispielsweise ein Grund für einen fehlenden Wert.""" From c828491be30eba17aa9f8bf5f87302a1b927af3a Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 11:05:23 +0100 Subject: [PATCH 10/11] use date in birthday --- src/bo4e/bo/person.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/bo4e/bo/person.py b/src/bo4e/bo/person.py index 5b69754d6..7bb077a97 100644 --- a/src/bo4e/bo/person.py +++ b/src/bo4e/bo/person.py @@ -3,9 +3,9 @@ and corresponding marshmallow schema for de-/serialization """ +from datetime import date from typing import TYPE_CHECKING, Annotated, Literal, Optional -import pydantic from pydantic import Field from ..enum.typ import Typ @@ -53,7 +53,7 @@ class Person(Geschaeftsobjekt): """Nachname (Familienname) der Person""" kontaktwege: Optional[list["Kontaktweg"]] = None """Kontaktwege der Person""" - geburtsdatum: Optional[pydantic.AwareDatetime] = None + geburtsdatum: Optional[date] = None """Geburtsdatum der Person""" kommentar: Optional[str] = None """Weitere Informationen zur Person""" From 4d17cd6332ccdc1689dc1fbf1d89963fd7c197a3 Mon Sep 17 00:00:00 2001 From: kevin Date: Thu, 20 Mar 2025 11:07:05 +0100 Subject: [PATCH 11/11] fix zeitreihenwert test --- tests/test_zeitreihenwert.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_zeitreihenwert.py b/tests/test_zeitreihenwert.py index cf7529e63..80f27530f 100644 --- a/tests/test_zeitreihenwert.py +++ b/tests/test_zeitreihenwert.py @@ -13,7 +13,7 @@ class TestZeitreihenwert: [ pytest.param( Zeitreihenwert( - zeitspanne=Zeitraum(startdatum=datetime(2013, 5, 1), enddatum=datetime(2022, 1, 28)), + zeitraum=Zeitraum(startdatum=datetime(2013, 5, 1), enddatum=datetime(2022, 1, 28)), wert=Decimal(2.5), status=Messwertstatus.ABGELESEN, statuszusatz=Messwertstatuszusatz.Z78_GERAETEWECHSEL,