f3-data-models 0.4.4__tar.gz → 0.5.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {f3_data_models-0.4.4 → f3_data_models-0.5.0}/PKG-INFO +1 -1
- {f3_data_models-0.4.4 → f3_data_models-0.5.0}/f3_data_models/models.py +136 -23
- f3_data_models-0.5.0/f3_data_models/testing.py +27 -0
- {f3_data_models-0.4.4 → f3_data_models-0.5.0}/f3_data_models/utils.py +7 -3
- {f3_data_models-0.4.4 → f3_data_models-0.5.0}/pyproject.toml +1 -1
- f3_data_models-0.4.4/f3_data_models/testing.py +0 -13
- {f3_data_models-0.4.4 → f3_data_models-0.5.0}/README.md +0 -0
- {f3_data_models-0.4.4 → f3_data_models-0.5.0}/f3_data_models/__init__.py +0 -0
@@ -6,6 +6,7 @@ from citext import CIText
|
|
6
6
|
from sqlalchemy import (
|
7
7
|
ARRAY,
|
8
8
|
JSON,
|
9
|
+
REAL,
|
9
10
|
TEXT,
|
10
11
|
TIME,
|
11
12
|
UUID,
|
@@ -509,6 +510,25 @@ class EventType_x_Event(Base):
|
|
509
510
|
event: Mapped["Event"] = relationship(back_populates="event_x_event_types")
|
510
511
|
|
511
512
|
|
513
|
+
class EventType_x_EventInstance(Base):
|
514
|
+
"""
|
515
|
+
Model representing the association between event instances and event types. The intention is that a single event instance can be associated with multiple event types.
|
516
|
+
|
517
|
+
Attributes:
|
518
|
+
event_instance_id (int): The ID of the associated event instance.
|
519
|
+
event_type_id (int): The ID of the associated event type.
|
520
|
+
|
521
|
+
event_instance (EventInstance): The associated event instance.
|
522
|
+
""" # noqa: E501
|
523
|
+
|
524
|
+
__tablename__ = "event_instances_x_event_types"
|
525
|
+
|
526
|
+
event_instance_id: Mapped[int] = mapped_column(ForeignKey("event_instances.id"), primary_key=True)
|
527
|
+
event_type_id: Mapped[int] = mapped_column(ForeignKey("event_types.id"), primary_key=True)
|
528
|
+
|
529
|
+
event_instance: Mapped["EventInstance"] = relationship(back_populates="event_instances_x_event_types")
|
530
|
+
|
531
|
+
|
512
532
|
class EventTag(Base):
|
513
533
|
"""
|
514
534
|
Model representing an event tag. These are used to mark special events, such as anniversaries or special workouts.
|
@@ -552,6 +572,24 @@ class EventTag_x_Event(Base):
|
|
552
572
|
|
553
573
|
event: Mapped["Event"] = relationship(back_populates="event_x_event_tags")
|
554
574
|
|
575
|
+
class EventTag_x_EventInstance(Base):
|
576
|
+
"""
|
577
|
+
Model representing the association between event tags and event instances. The intention is that a single event instance can be associated with multiple event tags.
|
578
|
+
|
579
|
+
Attributes:
|
580
|
+
event_instance_id (int): The ID of the associated event instance.
|
581
|
+
event_tag_id (int): The ID of the associated event tag.
|
582
|
+
|
583
|
+
event_instance (EventInstance): The associated event instance.
|
584
|
+
""" # noqa: E501
|
585
|
+
|
586
|
+
__tablename__ = "event_tags_x_event_instances"
|
587
|
+
|
588
|
+
event_instance_id: Mapped[int] = mapped_column(ForeignKey("event_instances.id"), primary_key=True)
|
589
|
+
event_tag_id: Mapped[int] = mapped_column(ForeignKey("event_tags.id"), primary_key=True)
|
590
|
+
|
591
|
+
event_instance: Mapped["EventInstance"] = relationship(back_populates="event_tags_x_event_instances")
|
592
|
+
|
555
593
|
|
556
594
|
class Org_x_SlackSpace(Base):
|
557
595
|
"""
|
@@ -643,12 +681,6 @@ class Event(Base):
|
|
643
681
|
index_within_interval (Optional[int]): The index within the recurrence interval. (e.g. 2nd Tuesday of the month).
|
644
682
|
pax_count (Optional[int]): The number of participants.
|
645
683
|
fng_count (Optional[int]): The number of first-time participants.
|
646
|
-
preblast (Optional[text]): The pre-event announcement.
|
647
|
-
backblast (Optional[text]): The post-event report.
|
648
|
-
preblast_rich (Optional[Dict[str, Any]]): The rich text pre-event announcement (e.g. Slack message).
|
649
|
-
backblast_rich (Optional[Dict[str, Any]]): The rich text post-event report (e.g. Slack message).
|
650
|
-
preblast_ts (Optional[float]): The Slack post timestamp of the pre-event announcement.
|
651
|
-
backblast_ts (Optional[float]): The Slack post timestamp of the post-event report.
|
652
684
|
meta (Optional[Dict[str, Any]]): Additional metadata for the event.
|
653
685
|
created (datetime): The timestamp when the record was created.
|
654
686
|
updated (datetime): The timestamp when the record was last updated.
|
@@ -667,7 +699,6 @@ class Event(Base):
|
|
667
699
|
org_id: Mapped[int] = mapped_column(ForeignKey("orgs.id"))
|
668
700
|
location_id: Mapped[Optional[int]] = mapped_column(ForeignKey("locations.id"))
|
669
701
|
series_id: Mapped[Optional[int]] = mapped_column(ForeignKey("events.id"))
|
670
|
-
is_series: Mapped[bool] = mapped_column(Boolean, default=False)
|
671
702
|
is_active: Mapped[bool] = mapped_column(Boolean, default=True)
|
672
703
|
highlight: Mapped[bool] = mapped_column(Boolean, default=False)
|
673
704
|
start_date: Mapped[date]
|
@@ -681,14 +712,6 @@ class Event(Base):
|
|
681
712
|
recurrence_pattern: Mapped[Optional[Event_Cadence]]
|
682
713
|
recurrence_interval: Mapped[Optional[int]]
|
683
714
|
index_within_interval: Mapped[Optional[int]]
|
684
|
-
pax_count: Mapped[Optional[int]]
|
685
|
-
fng_count: Mapped[Optional[int]]
|
686
|
-
preblast: Mapped[Optional[text]]
|
687
|
-
backblast: Mapped[Optional[text]]
|
688
|
-
preblast_rich: Mapped[Optional[Dict[str, Any]]]
|
689
|
-
backblast_rich: Mapped[Optional[Dict[str, Any]]]
|
690
|
-
preblast_ts: Mapped[Optional[float]]
|
691
|
-
backblast_ts: Mapped[Optional[float]]
|
692
715
|
meta: Mapped[Optional[Dict[str, Any]]]
|
693
716
|
created: Mapped[dt_create]
|
694
717
|
updated: Mapped[dt_update]
|
@@ -716,7 +739,97 @@ class Event(Base):
|
|
716
739
|
event_x_event_tags: Mapped[Optional[List[EventTag_x_Event]]] = relationship(
|
717
740
|
back_populates="event", cascade="save-update, merge, delete"
|
718
741
|
)
|
719
|
-
|
742
|
+
|
743
|
+
|
744
|
+
class EventInstance(Base):
|
745
|
+
"""
|
746
|
+
Model representing an event instance (a single occurrence of an event).
|
747
|
+
|
748
|
+
Attributes:
|
749
|
+
id (int): Primary Key of the model.
|
750
|
+
org_id (int): The ID of the associated organization.
|
751
|
+
location_id (Optional[int]): The ID of the associated location.
|
752
|
+
series_id (Optional[int]): The ID of the associated event series.
|
753
|
+
is_active (bool): Whether the event is active. Default is True.
|
754
|
+
highlight (bool): Whether the event is highlighted. Default is False.
|
755
|
+
start_date (date): The start date of the event.
|
756
|
+
end_date (Optional[date]): The end date of the event.
|
757
|
+
start_time (Optional[str]): The start time of the event. Format is 'HHMM', 24-hour time, timezone naive.
|
758
|
+
end_time (Optional[str]): The end time of the event. Format is 'HHMM', 24-hour time, timezone naive.
|
759
|
+
name (str): The name of the event.
|
760
|
+
description (Optional[text]): A description of the event.
|
761
|
+
email (Optional[str]): A contact email address associated with the event.
|
762
|
+
pax_count (Optional[int]): The number of participants.
|
763
|
+
fng_count (Optional[int]): The number of first-time participants.
|
764
|
+
preblast (Optional[text]): The pre-event announcement.
|
765
|
+
backblast (Optional[text]): The post-event report.
|
766
|
+
preblast_rich (Optional[Dict[str, Any]]): The rich text pre-event announcement (e.g. Slack message).
|
767
|
+
backblast_rich (Optional[Dict[str, Any]]): The rich text post-event report (e.g. Slack message).
|
768
|
+
preblast_ts (Optional[float]): The Slack post timestamp of the pre-event announcement.
|
769
|
+
backblast_ts (Optional[float]): The Slack post timestamp of the post-event report.
|
770
|
+
meta (Optional[Dict[str, Any]]): Additional metadata for the event.
|
771
|
+
created (datetime): The timestamp when the record was created.
|
772
|
+
updated (datetime): The timestamp when the record was last updated.
|
773
|
+
|
774
|
+
org (Org): The associated organization.
|
775
|
+
location (Location): The associated location.
|
776
|
+
event_types (List[EventType]): The associated event types.
|
777
|
+
event_tags (Optional[List[EventTag]]): The associated event tags.
|
778
|
+
event_x_event_types (List[EventType_x_Event]): The association between the event and event types.
|
779
|
+
event_x_event_tags (Optional[List[EventTag_x_Event]]): The association between the event and event tags.
|
780
|
+
""" # noqa: E501
|
781
|
+
|
782
|
+
__tablename__ = "event_instances"
|
783
|
+
|
784
|
+
id: Mapped[intpk]
|
785
|
+
org_id: Mapped[int] = mapped_column(ForeignKey("orgs.id"))
|
786
|
+
location_id: Mapped[Optional[int]] = mapped_column(ForeignKey("locations.id"))
|
787
|
+
series_id: Mapped[Optional[int]] = mapped_column(ForeignKey("events.id"))
|
788
|
+
is_active: Mapped[bool] = mapped_column(Boolean, default=True)
|
789
|
+
highlight: Mapped[bool] = mapped_column(Boolean, default=False)
|
790
|
+
start_date: Mapped[date]
|
791
|
+
end_date: Mapped[Optional[date]]
|
792
|
+
start_time: Mapped[Optional[str]]
|
793
|
+
end_time: Mapped[Optional[str]]
|
794
|
+
name: Mapped[str]
|
795
|
+
description: Mapped[Optional[text]]
|
796
|
+
email: Mapped[Optional[str]]
|
797
|
+
pax_count: Mapped[Optional[int]]
|
798
|
+
fng_count: Mapped[Optional[int]]
|
799
|
+
preblast: Mapped[Optional[text]]
|
800
|
+
backblast: Mapped[Optional[text]]
|
801
|
+
preblast_rich: Mapped[Optional[Dict[str, Any]]]
|
802
|
+
backblast_rich: Mapped[Optional[Dict[str, Any]]]
|
803
|
+
preblast_ts: Mapped[Optional[float]]
|
804
|
+
backblast_ts: Mapped[Optional[float]]
|
805
|
+
meta: Mapped[Optional[Dict[str, Any]]]
|
806
|
+
created: Mapped[dt_create]
|
807
|
+
updated: Mapped[dt_update]
|
808
|
+
|
809
|
+
__table_args__ = (
|
810
|
+
Index("idx_event_instances_org_id", "org_id"),
|
811
|
+
Index("idx_event_instances_location_id", "location_id"),
|
812
|
+
Index("idx_event_instances_is_active", "is_active"),
|
813
|
+
)
|
814
|
+
|
815
|
+
org: Mapped[Org] = relationship(innerjoin=True, cascade="expunge", viewonly=True)
|
816
|
+
location: Mapped[Location] = relationship(innerjoin=True, cascade="expunge", viewonly=True)
|
817
|
+
event_types: Mapped[List[EventType]] = relationship(
|
818
|
+
secondary="event_instances_x_event_types",
|
819
|
+
innerjoin=True,
|
820
|
+
cascade="expunge",
|
821
|
+
viewonly=True,
|
822
|
+
)
|
823
|
+
event_tags: Mapped[Optional[List[EventTag]]] = relationship(
|
824
|
+
secondary="event_tags_x_event_instances", cascade="expunge", viewonly=True
|
825
|
+
)
|
826
|
+
event_instances_x_event_types: Mapped[List[EventType_x_EventInstance]] = relationship(
|
827
|
+
back_populates="event_instances", cascade="save-update, merge, delete"
|
828
|
+
)
|
829
|
+
event_instances_x_event_tags: Mapped[Optional[List[EventTag_x_EventInstance]]] = relationship(
|
830
|
+
back_populates="event_instance", cascade="save-update, merge, delete"
|
831
|
+
)
|
832
|
+
attendance: Mapped[List["Attendance"]] = relationship(back_populates="event_instance", cascade="expunge, delete")
|
720
833
|
|
721
834
|
|
722
835
|
class AttendanceType(Base):
|
@@ -849,14 +962,14 @@ class Attendance(Base):
|
|
849
962
|
|
850
963
|
Attributes:
|
851
964
|
id (int): Primary Key of the model.
|
852
|
-
|
965
|
+
event_instance_id (int): The ID of the associated event instance.
|
853
966
|
user_id (Optional[int]): The ID of the associated user.
|
854
967
|
is_planned (bool): Whether this is planned attendance (True) vs actual attendance (False).
|
855
968
|
meta (Optional[Dict[str, Any]]): Additional metadata for the attendance.
|
856
969
|
created (datetime): The timestamp when the record was created.
|
857
970
|
updated (datetime): The timestamp when the record was last updated.
|
858
971
|
|
859
|
-
|
972
|
+
event_instance (EventInstance): The associated event instance.
|
860
973
|
user (User): The associated user.
|
861
974
|
slack_user (Optional[SlackUser]): The associated Slack user.
|
862
975
|
attendance_x_attendance_types (List[Attendance_x_AttendanceType]): The association between the attendance and attendance types.
|
@@ -864,17 +977,17 @@ class Attendance(Base):
|
|
864
977
|
""" # noqa: E501
|
865
978
|
|
866
979
|
__tablename__ = "attendance"
|
867
|
-
__table_args__ = (UniqueConstraint("
|
980
|
+
__table_args__ = (UniqueConstraint("event_instance_id", "user_id", "is_planned"),)
|
868
981
|
|
869
982
|
id: Mapped[intpk]
|
870
|
-
|
983
|
+
event_instance_id: Mapped[int] = mapped_column(ForeignKey("event_instances.id"))
|
871
984
|
user_id: Mapped[int] = mapped_column(ForeignKey("users.id"))
|
872
985
|
is_planned: Mapped[bool]
|
873
986
|
meta: Mapped[Optional[Dict[str, Any]]]
|
874
987
|
created: Mapped[dt_create]
|
875
988
|
updated: Mapped[dt_update]
|
876
989
|
|
877
|
-
|
990
|
+
event_instance: Mapped[EventInstance] = relationship(innerjoin=True, cascade="expunge", viewonly=True)
|
878
991
|
user: Mapped[User] = relationship(innerjoin=True, cascade="expunge", viewonly=True)
|
879
992
|
slack_user: Mapped[Optional[SlackUser]] = relationship(
|
880
993
|
innerjoin=False, cascade="expunge", secondary="users", viewonly=True
|
@@ -1185,8 +1298,8 @@ class UpdateRequest(Base):
|
|
1185
1298
|
location_state: Mapped[Optional[str]]
|
1186
1299
|
location_zip: Mapped[Optional[str]]
|
1187
1300
|
location_country: Mapped[Optional[str]]
|
1188
|
-
location_lat: Mapped[Optional[float]] = mapped_column(
|
1189
|
-
location_lng: Mapped[Optional[float]] = mapped_column(
|
1301
|
+
location_lat: Mapped[Optional[float]] = mapped_column(REAL())
|
1302
|
+
location_lng: Mapped[Optional[float]] = mapped_column(REAL())
|
1190
1303
|
location_id: Mapped[Optional[int]] = mapped_column(ForeignKey("locations.id"))
|
1191
1304
|
location_contact_email: Mapped[Optional[str]]
|
1192
1305
|
|
@@ -0,0 +1,27 @@
|
|
1
|
+
from f3_data_models.models import Location
|
2
|
+
from f3_data_models.utils import DbManager
|
3
|
+
|
4
|
+
|
5
|
+
def test_update_event():
|
6
|
+
DbManager.update_record(
|
7
|
+
Location,
|
8
|
+
2,
|
9
|
+
{
|
10
|
+
"name": "The Beach",
|
11
|
+
"description": None,
|
12
|
+
"is_active": True,
|
13
|
+
"latitude": 22.0356,
|
14
|
+
"longitude": -159.3377,
|
15
|
+
"address_street": None,
|
16
|
+
"address_street2": None,
|
17
|
+
"address_city": None,
|
18
|
+
"address_state": None,
|
19
|
+
"address_zip": None,
|
20
|
+
"address_country": None,
|
21
|
+
"org_id": 5,
|
22
|
+
},
|
23
|
+
)
|
24
|
+
|
25
|
+
|
26
|
+
if __name__ == "__main__":
|
27
|
+
test_update_event()
|
@@ -10,7 +10,6 @@ from sqlalchemy import Select, and_, inspect, select
|
|
10
10
|
from sqlalchemy.dialects.postgresql import insert
|
11
11
|
from sqlalchemy.engine import Engine
|
12
12
|
from sqlalchemy.orm import class_mapper, joinedload, sessionmaker
|
13
|
-
from sqlalchemy.orm.attributes import InstrumentedAttribute
|
14
13
|
from sqlalchemy.orm.collections import InstrumentedList
|
15
14
|
from sqlalchemy_schemadisplay import create_schema_graph
|
16
15
|
|
@@ -158,9 +157,13 @@ class DbManager:
|
|
158
157
|
relationships = mapper.relationships.keys()
|
159
158
|
for attr, value in fields.items():
|
160
159
|
key = attr if isinstance(attr, str) else attr.key
|
160
|
+
print(f"key: {key}, value: {value}")
|
161
161
|
if hasattr(cls, key) and key not in relationships:
|
162
|
-
|
163
|
-
|
162
|
+
setattr(record, key, value)
|
163
|
+
# if isinstance(attr, InstrumentedAttribute):
|
164
|
+
# setattr(record, key, value)
|
165
|
+
# else:
|
166
|
+
# setattr(record, key, value)
|
164
167
|
elif key in relationships:
|
165
168
|
# Handle relationships separately
|
166
169
|
relationship = mapper.relationships[key]
|
@@ -189,6 +192,7 @@ class DbManager:
|
|
189
192
|
session.add(related_record)
|
190
193
|
|
191
194
|
try:
|
195
|
+
print(record)
|
192
196
|
session.commit()
|
193
197
|
except pg8000.IntegrityError as e:
|
194
198
|
session.rollback()
|
@@ -1,13 +0,0 @@
|
|
1
|
-
from f3_data_models.models import User
|
2
|
-
from f3_data_models.utils import DbManager
|
3
|
-
|
4
|
-
|
5
|
-
def test_update_event():
|
6
|
-
user = User(
|
7
|
-
email="evan.Petzoldt@protonmail.com",
|
8
|
-
)
|
9
|
-
DbManager.create_record(user)
|
10
|
-
|
11
|
-
|
12
|
-
if __name__ == "__main__":
|
13
|
-
test_update_event()
|
File without changes
|
File without changes
|