membershipworks: Convert EventMeetingTime to subclass of Reservation
This commit is contained in:
parent
35c063c44e
commit
e4280361d1
@ -103,11 +103,12 @@ class TransactionAdmin(BaseMembershipWorksAdmin):
|
||||
|
||||
class EventMeetingTimeInline(admin.TabularInline):
|
||||
model = EventMeetingTime
|
||||
fields = ["start", "end", "duration", "resources"]
|
||||
readonly_fields = ["duration"]
|
||||
autocomplete_fields = ["resources"]
|
||||
extra = 0
|
||||
min_num = 1
|
||||
|
||||
readonly_fields = ["duration"]
|
||||
|
||||
|
||||
@admin.register(EventInstructor)
|
||||
class EventInstructorAdmin(admin.ModelAdmin):
|
||||
|
@ -0,0 +1,82 @@
|
||||
# Generated by Django 5.0.7 on 2024-07-30 23:10
|
||||
|
||||
import django.db.models.deletion
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
def convert_meetingtimes_to_reservations(apps, schema_editor):
|
||||
Reservation = apps.get_model("reservations", "Reservation")
|
||||
EventMeetingTime = apps.get_model("membershipworks", "EventMeetingTime")
|
||||
for meeting_time in EventMeetingTime.objects.all():
|
||||
reservation = Reservation.objects.create(
|
||||
id=meeting_time.id,
|
||||
start=meeting_time.start,
|
||||
end=meeting_time.end,
|
||||
)
|
||||
meeting_time.reservation_ptr = reservation
|
||||
meeting_time.save()
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
dependencies = [
|
||||
("membershipworks", "0019_eventext_should_survey_eventext_survey_email_sent"),
|
||||
("reservations", "0001_initial"),
|
||||
]
|
||||
|
||||
operations = [
|
||||
# add reservation field
|
||||
migrations.AddField(
|
||||
model_name="eventmeetingtime",
|
||||
name="reservation_ptr",
|
||||
field=models.OneToOneField(
|
||||
auto_created=True,
|
||||
null=True,
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
parent_link=True,
|
||||
serialize=False,
|
||||
to="reservations.reservation",
|
||||
),
|
||||
preserve_default=False,
|
||||
),
|
||||
migrations.RunPython(convert_meetingtimes_to_reservations, atomic=True),
|
||||
# remove primary key
|
||||
migrations.RemoveField(
|
||||
model_name="eventmeetingtime",
|
||||
name="id",
|
||||
),
|
||||
# make reservation non-nullable
|
||||
migrations.AlterField(
|
||||
model_name="eventmeetingtime",
|
||||
name="reservation_ptr",
|
||||
field=models.OneToOneField(
|
||||
auto_created=True,
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
parent_link=True,
|
||||
primary_key=True,
|
||||
serialize=False,
|
||||
to="reservations.reservation",
|
||||
),
|
||||
preserve_default=False,
|
||||
),
|
||||
# delete old columns
|
||||
migrations.RemoveConstraint(
|
||||
model_name="eventmeetingtime",
|
||||
name="unique_event_start_end",
|
||||
),
|
||||
migrations.RemoveConstraint(
|
||||
model_name="eventmeetingtime",
|
||||
name="end_after_start",
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name="eventmeetingtime",
|
||||
name="duration",
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name="eventmeetingtime",
|
||||
name="end",
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name="eventmeetingtime",
|
||||
name="start",
|
||||
),
|
||||
]
|
@ -30,6 +30,8 @@ import nh3
|
||||
from django_db_views.db_view import DBView
|
||||
from django_stubs_ext import WithAnnotations
|
||||
|
||||
from reservations.models import Reservation
|
||||
|
||||
|
||||
class BaseModel(models.Model):
|
||||
_api_names_override: dict[str, str] = {}
|
||||
@ -619,29 +621,27 @@ else:
|
||||
EventExtAnnotatedWithFinancials = WithAnnotations[EventExt]
|
||||
|
||||
|
||||
class EventMeetingTime(models.Model):
|
||||
class EventMeetingTime(Reservation):
|
||||
event = models.ForeignKey(
|
||||
EventExt, on_delete=models.CASCADE, related_name="meeting_times"
|
||||
)
|
||||
start = models.DateTimeField()
|
||||
end = models.DateTimeField()
|
||||
|
||||
duration = models.GeneratedField(
|
||||
expression=F("end") - F("start"),
|
||||
output_field=models.DurationField(),
|
||||
db_persist=False,
|
||||
# TODO: should probably do some validation in python to enforce
|
||||
# - uniqueness and non-overlapping (per event)
|
||||
# - min/max start/end time == event start end
|
||||
|
||||
def make_google_calendar_event(self):
|
||||
status = (
|
||||
"confirmed"
|
||||
if self.event.cap > 0 and self.event.calendar != Event.EventCalendar.HIDDEN
|
||||
else "cancelled"
|
||||
)
|
||||
|
||||
class Meta:
|
||||
constraints = [
|
||||
models.UniqueConstraint(
|
||||
fields=["event", "start", "end"], name="unique_event_start_end"
|
||||
),
|
||||
models.CheckConstraint(check=Q(end__gt=F("start")), name="end_after_start"),
|
||||
]
|
||||
|
||||
def __str__(self) -> str:
|
||||
return f"{self.start} - {self.end}"
|
||||
return super().make_google_calendar_event() | {
|
||||
# TODO: add event description and links
|
||||
"summary": self.event.unescaped_title,
|
||||
"status": status,
|
||||
}
|
||||
|
||||
|
||||
class EventInvoice(models.Model):
|
||||
|
Loading…
Reference in New Issue
Block a user