Skip to content
David Moore edited this page Sep 1, 2020 · 15 revisions

Why are there several different event types?

A discussion document. Please add your suggestions and thoughts.

Why are there several different event types? All events could be entered as MultidayRecurringEventPage with the "until date" set the same as "from date" if they don't repeat and with "number of days" set to 1 if the event occurs over just the one day.

In part it is just the way the library evolved. Simple events were coded first, then multiday events, then recurring events, each as a new event type. But mainly it is for usability. We ask the user for the type of event up front and then we only display the options that make sense for that kind of event.

So the database has completely separate models for SimpleEventPage, MultidayEventPage, RecurringEventPage and PostponementPage. Each of which must be queried to get all the events occurring. This seems clumsy. [Django-Polymorphic or Django-Model-Utils InheritanceManager could be used to fix this?] It also means it is not easy to convert an event from one type to another. The user must create a new event, manually copy the data over, and then delete the old one.

When MultidayRecurringEventPage was added I used a different technique. I modified RecurringEventPage to add a num_days field, but hide it from being displayed. MultidayRecurringEventPage exists just as a proxy model which exposes this field. It does not exist as a separate model in the database. But Wagtail does not have great support for proxy models (Issue 4973) and so this requires the trickery of HiddenNumDaysPanel, as trying to edit a MultidayRecurringEventPage will bring up the form for RecurringEventPage instead. [As at 2020-08-23: Not any more. Time to re-investigate ProxyModels? The issue is still open, but things have improved. Try converting MultidayEvents into a proxy model?] The calculations for status, when, and _getMyFirstDatetimeTo take account of num_days, so separate versions of these are not required for RecurringEventPage and MultidayRecurringEventPage.

If EventBase which all the event types inherit from was not abstract, there would be a row in the EventBase table for every event that existed regardless of its type. EventBase could hold date_from and date_to fields which could be used so queries would only have to refer to the EventBase table. date_to would be hidden for SimpleEventPage and would equal the repeat until subfield for RecurringEventPage. RecurringEventPages would require further filtering by their repeat field. When proxy models are better supported they could be used for SimpleEventPage, and MultidayEventPage as these then would have no extra fields needing to be stored. RecurringEventPage and PostponementPage do and would need to be concrete models. PostponementPage is interesting as it is both an event and an exception combining the work of a Cancellation with a new SimpleEventPage or MultidayEventPage.

Another approach would be to combine all the fields into one omni-event model and also store what type of event it is. Then use Javascript on the form to hide or display the relevant fields.

Questions for users of Joyous:

Do you care what database structure Joyous uses to store events?

How easy do you find the experience of creating a new event?

Have you ever wanted to convert an event from one type to another - e.g. change a one-off event into a recurring event?

Do you have any custom event querying code? If so are you using the API get functions (getAllEventsByDay, getAllEventsByWeek, getAllUpcomingEvents, etc), the EventQuerySets (RecurringEventPage.events.upcoming etc), plain Django code, or something else?