class IntervalNotification(models.Model): """ Notifications sent to users when a specified period has elapsed. This class is also proof-of-concept, and it relies upon the `Amazon Simple Email Service <http://aws.amazon.com/ses/>`_. An email will be sent to users who opt in to the notification summarizing their devices' energy usage over the specified period. """ description = models.CharField( max_length=300, help_text="Label to notification as shown to a user", ) """ The description of the event notification as a user would see it when selecting/deselecting the notification in the settings interface""" recurrences = RecurrenceField(blank=True, null=True) """ This field is treated much like a Google Calendars recurrence field. Provides an easy way for an admin to define new periods of time.""" email_subject = models.CharField(max_length=300) """ An email-friendly subject for the event notification.""" email_body = models.FileField( help_text= "Template file for email body. {{ x }} denotes template variable", upload_to="interval") """ A template used to generate the notification email body.""" def __unicode__(self): return self.description
class Campaign(models.Model): uuid = models.UUIDField(default=uuid.uuid4, editable=False, unique=True) name = models.CharField(max_length=255) description = models.TextField() owner = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE) start = models.DateTimeField() end = models.DateTimeField(null=True) recurrence = RecurrenceField() def get_rule(self): if self.recurrence.rrules is not None: if len(self.recurrence.rrules) > 0: return serialize(self.recurrence.rrules[0]) return None def set_rule(self, i): self.recurrence = deserialize(i) rule = property(get_rule, set_rule) # FIXME: Disabled during lack of original code # choice = models.CharField() # segment = models.ForeignKey() # node = models.ForeignKey() active = models.BooleanField(default=False) created = models.DateTimeField(auto_now_add=True) modified = models.DateTimeField(auto_now=True)
class Schedule(models.Model): project = models.ForeignKey(Project, on_delete=models.CASCADE, verbose_name='プロジェクト') name = models.CharField('名前', max_length=50) description = models.TextField('説明', blank=True) place = models.CharField('場所', max_length=50, blank=True) date = models.DateField('日付') time_from = models.TimeField('開始時間', blank=True, null=True) time_to = models.TimeField('終了時間', blank=True, null=True) recurrence = RecurrenceField(include_dtstart=False, blank=True, verbose_name='繰り返し条件') recur_until = models.DateField('繰り返し終了日', blank=True, null=True) author = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE, related_name='authored_schedules', verbose_name='作成者') participants = models.ManyToManyField(settings.AUTH_USER_MODEL, blank=True, related_name='participated_schedules', verbose_name='参加者') def get_occurence_dates(self, start, end): if start < self.date: start = self.date if self.recur_until < end: end = self.recur_until if end < start: return [] return self.recurrence.between(start, end, dtstart=start, inc=True) class Meta: verbose_name = '予定' verbose_name_plural = '予定'
class Expense(models.Model): budgeted_amount = models.FloatField() budgeted_date = models.DateField(null=True, blank=True) income = models.ForeignKey(Income, on_delete=models.SET_NULL, null=True, blank=True) description = models.CharField(max_length=1000) first_occurrence = models.ForeignKey("self", null=True, blank=True, on_delete=models.PROTECT) recurrences = RecurrenceField(null=True, blank=True, include_dtstart=False) transaction = models.ForeignKey("Transaction", null=True, blank=True, on_delete=models.PROTECT) def __str__(self): args = [self.description, self.income] if self.transaction: args.append(abs(self.transaction.amout)) else: args.append(self.budgeted_amount) return '{0} - {1} (${2})'.format(*args)
class Scan(models.Model): """Model for a type of Scan.""" id = models.AutoField(primary_key=True, verbose_name="Scan ID") site = models.ForeignKey(Site, on_delete=models.CASCADE, verbose_name="Site ID") scan_name = models.CharField(unique=False, max_length=255, blank=True, verbose_name="Scan Name") start_time = models.TimeField(verbose_name="Scan start time") recurrences = RecurrenceField(include_dtstart=False, verbose_name="Recurrences") def __str__(self): return str(self.id) # def get_text_rules_inclusion(self): # schedule_scan = ScheduledScan.objects.get(id=self.id) # text_rules_inclusion = [] # # for rule in schedule_scan.recurrences.rrules: # text_rules_inclusion.append(rule.to_text()) # # print(text_rules_inclusion) # return text_rules_inclusion class Meta: verbose_name_plural = "Scans"
class Event(models.Model): creator = models.ForeignKey( AUTH_USER_MODEL, models.CASCADE, null=True, ) title = models.CharField(max_length=200, blank=True, null=True) created = models.DateTimeField(blank=True, auto_now_add=True, null=True) start_date = models.DateField(blank=True, null=True) # end_date = models.DateField(blank=True, null=True) start_time = models.TimeField(null=True, blank=True) end_time = models.TimeField(null=True, blank=True) place = models.CharField(max_length=250, null=True, blank=True) type = models.ForeignKey(TypeEvent, on_delete=models.SET_NULL, null=True, blank=True) description = models.CharField(max_length=250, null=True, blank=True) party = models.ManyToManyField(AUTH_USER_MODEL, blank=True, related_name="member_events") room = models.ForeignKey(Group, on_delete=models.SET_NULL, null=True, blank=True) recurrences = RecurrenceField() def __str__(self): return f"id:{self.id} {self.start_date} {self.title}" def save(self, *args, **kwargs): if not self.start_date: self.start_date = datetime.datetime.now().date() super(Event, self).save(*args, **kwargs)
class ResourceSlot(models.Model): resource = models.ForeignKey(Resource, on_delete=models.CASCADE) creator = models.ForeignKey(User, on_delete=models.CASCADE) start_date_time = models.DateTimeField(default=timezone.now) end_date_time = models.DateTimeField(default=timezone.now() + timezone.timedelta(hours=1)) description = models.TextField() approved = models.BooleanField(default=False) recurrences = RecurrenceField() def get_no_of_participants(self): return self.participants.count() def clean(self): time_diff = self.end_date_time - self.start_date_time hours = divmod(time_diff.total_seconds(), 3600)[0] if self.start_date_time > self.end_date_time: raise ValidationError({ 'start_date_time': 'Start Date cannot be greater than End date' }) if hours > 24: raise ValidationError( {'end_date_time': 'End date cannot be more than 24 hours'}) if (not self._validate_date(self.start_date_time) or not self._validate_date(self.start_date_time)): msg = 'Only current month booking is allowed' raise ValidationError({'start_date_time': msg}) if not self.id: query = dedent("""\ select id from website_resourceslot where %s between start_date_time and end_date_time and resource_id = %s """) slot = ResourceSlot.objects.raw( query, [self.start_date_time, self.resource.id]) if slot: msg = 'Slot is already booked for {0}'.format(self.resource) raise ValidationError({'start_date_time': msg}) def _validate_date(self, date): now = timezone.now() return date.month == now.month and date.year == now.year def toggle_approval_status(self): if self.approved: self.approved = False else: self.approved = True self.save() def set_approval_status(self): self.approved = True self.save() def reset_approval_status(self): self.approved = False self.save() def __str__(self): return "Slot for {0}".format(self.resource.name)
class Gathering(models.Model): # airtableID = models.CharField(max_length=20, blank=True, null=True) # event = models.OneToOneField(Event, on_delete=models.CASCADE, primary_key=True, related_name='gathering') name = models.CharField(max_length=50) description = models.TextField() recurrences = RecurrenceField(null=True) start_time = models.TimeField() end_time = models.TimeField() location = models.CharField(max_length=50, null=True) category = models.CharField(max_length=2, choices=GATHERING_TYPES) authors = models.ManyToManyField(Person) @property def Date(self): next_date = self.recurrences.after(datetime.now()) if next_date: return next_date else: return self.recurrences.occurrences()[0] @property def recurrence_text(self): return " + ".join([rule.to_text() for rule in self.recurrences.rrules]) def __str__(self): return self.name
class Schedule(models.Model): LIVE = 'L' BROADCAST = 'B' BROADCAST_SYNDICATION = 'S' REPETITION = 'R' SCHEDULE_TYPE = ((LIVE, _("live")), (BROADCAST, _("broadcast")), (BROADCAST_SYNDICATION, _("broadcast syndication")), (REPETITION, _("repetition"))) class Meta: verbose_name = _('schedule') verbose_name_plural = _('schedules') slot = models.ForeignKey(Slot, verbose_name=_("slot")) type = models.CharField(verbose_name=_("type"), choices=SCHEDULE_TYPE, max_length=1) recurrences = RecurrenceField(verbose_name=_("recurrences")) source = models.ForeignKey('self', blank=True, null=True, on_delete=models.SET_NULL, verbose_name=_("source"), help_text=_("It is used when is a broadcast.")) @property def runtime(self): return self.slot.runtime @property def start(self): return self.recurrences.dtstart @start.setter def start(self, start_date): self.recurrences.dtstart = start_date @property def end(self): if not self.start: return None return self.start + self.runtime def dates_between(self, after, before): """ Return a sorted list of dates between after and before """ return self.recurrences.between(after, before, inc=True) def date_before(self, before): return self.recurrences.before(before, inc=True) def date_after(self, after, inc=True): return self.recurrences.after(after, inc=inc) def __str__(self): return ' - '.join( [self.start.strftime('%A'), self.start.strftime('%X')])
class Route(models.Model): """Маршрут""" name = models.CharField(max_length=255) recurrences = RecurrenceField() def __str__(self): return self.name
class Passeio(models.Model): id = models.AutoField(primary_key=True) duracao = models.DurationField() origem = models.TextField() local = models.TextField() data = models.DateField() descricaoPasseio = models.TextField() passeador = models.ForeignKey(Usuario, on_delete=models.CASCADE) pet = models.ForeignKey(Pet, on_delete=models.CASCADE) idRecorrencia = models.ForeignKey('self', on_delete=models.CASCADE, blank=True, default=None, null=True) recorrencias = RecurrenceField(include_dtstart=False, blank=True, default=None, null=True)
class TaskGroup(models.Model): created_at = models.DateTimeField(auto_now_add=True) updated_at = models.DateTimeField(auto_now=True) label = models.CharField(max_length=60) slug = models.SlugField(max_length=150, unique=True) created_by = models.ForeignKey( settings.AUTH_USER_MODEL, on_delete=models.CASCADE, related_name='taskgroups') recurrences = RecurrenceField(blank=True, null=True) def __str__(self): return self.label
class Flow(models.Model): name = models.CharField(max_length=20) memo = models.CharField(max_length=200, null=True, blank=True) initial = models.FloatField(default=0) start_date = models.DateTimeField() amount = models.FloatField() recurrence = RecurrenceField() goal = models.FloatField(blank=True, null=True) active = models.BooleanField(default=True) def __str__(self): return self.name
class Team(models.Model): def __str__(self): return self.name name=models.CharField(max_length=30) status=models.BooleanField(default=True, choices=[ (True, 'Active'), (False, 'Inactive')]) recurrences = RecurrenceField(null=True) time_in = models.TimeField(null=True) time_out = models.TimeField(null=True)
class MeetingTime(models.Model): """Models a meeting time.""" delivery_method = models.CharField(max_length=255, null=True, blank=True) start_date = models.DateTimeField(null=True) end_date = models.DateTimeField(null=True) start_time = models.TimeField(null=True, blank=True) end_time = models.TimeField(null=True, blank=True) recurrence = RecurrenceField(blank=True) course = ForeignKey(to=Course, related_name="meeting_times", on_delete=models.CASCADE) def __str__(self): """Return string representation.""" return f"{self.delivery_method} {self.start_date} {self.end_date}. {self.start_time} - {self.end_time}. {self.recurrence}"
class Task(TimeStampedModel): class Meta: verbose_name = "Auftrag" verbose_name_plural = "Aufträge" title = models.CharField(verbose_name="Titel", max_length=255) duration = models.DurationField(verbose_name="Dauer") rrule = RecurrenceField(verbose_name="rrule") customer = models.ForeignKey( Customer, verbose_name="Kunde", on_delete=models.CASCADE, related_name="tasks", )
class ScheduleRule(models.Model): playlist = models.ForeignKey(to=Playlist, on_delete=models.CASCADE) schedule = models.ForeignKey(to=Schedule, on_delete=models.CASCADE) starts = models.DateField() occurrences = RecurrenceField() start_time = models.TimeField() end_time = models.TimeField() priority = models.IntegerField() def is_expired(self): return not bool( self.occurrences.after( timezone.datetime.today() - timezone.timedelta(days=2), inc=True))
class Workshop(models.Model): """Instructor Creates workshop based on WorkshopTypes available""" workshop_instructor = models.ForeignKey(User, on_delete=models.CASCADE) workshop_title = models.ForeignKey( WorkshopType, on_delete=models.CASCADE, help_text=' [Select the type of workshop.] ') #For recurring workshops source: django-recurrence recurrences = RecurrenceField() def __str__(self): return u"{0} | {1} ".format(self.workshop_title, self.workshop_instructor)
class Scan(models.Model): """Model for a type of Scan.""" id = models.AutoField(primary_key=True, verbose_name="Scan ID") site = models.ForeignKey(Site, on_delete=models.CASCADE, verbose_name="Site ID") scan_name = models.CharField(unique=False, max_length=255, blank=True, verbose_name="Scan Name") enable_scan = models.BooleanField(verbose_name="Enable scan?") start_time = models.TimeField(verbose_name="Scan start time") recurrences = RecurrenceField(include_dtstart=False, verbose_name="Recurrences") dtstart = models.DateTimeField( blank=True, null=True, verbose_name= "dtstart is the seed datetime object for recurrences (automatically modifed)", ) created = models.DateTimeField(auto_now_add=True) last_updated = models.DateTimeField(auto_now=True, verbose_name="Last updated") # dtstart is the seed datetime object when determining scan_scheduler.py's # scan_occurrences = scan.recurrences.between(beginning_of_today, end_of_today, dtstart=dtstart, inc=True), # dtstart is updated on every Scan model save. Currently, both the date and time are updated for dtstart. Not sure # if updating the date really matters. def save(self, *args, **kwargs): # current_scan = Scan.objects.get(pk=self.pk) # if self.start_time != current_scan.start_time: # if self.recurrences != current_scan.recurrences: now_datetime = localtime(now()) self.dtstart = (now_datetime.replace( hour=self.start_time.hour).replace( minute=self.start_time.minute).replace(second=0).replace( microsecond=0)) return super().save(*args, **kwargs) def __str__(self): return str(self.id) class Meta: verbose_name_plural = "Scans"
class Schedule(BaseModel): """ Schedule model """ name = models.CharField(max_length=200, blank=True) start_date = models.DateField(default=now) end_date = models.DateField(blank=True, null=True) all_day = models.BooleanField(default=False, blank=True) start_time = models.TimeField(blank=True, null=True) end_time = models.TimeField(blank=True, null=True) is_recurring = models.BooleanField(default=False, blank=True) recurrence_pattern = RecurrenceField(blank=True, null=True) business = models.ForeignKey( Business, on_delete=models.CASCADE, related_name='available', blank=True, null=True) menu = models.ForeignKey(Menu, on_delete=models.CASCADE, related_name='available', blank=True, null=True) class Meta: ordering = []
class Summary(models.Model): """The necessary configuration for summary reports.""" name = models.CharField(max_length=256, unique=True, null=False, verbose_name='Navn') description = models.TextField(verbose_name='Beskrivelse', null=True, blank=True) schedule = RecurrenceField(max_length=1024, verbose_name='Planlagt afvikling') last_run = models.DateTimeField(blank=True, null=True, verbose_name='Sidste kørsel') recipients = models.ManyToManyField(UserProfile, blank=True, verbose_name="Modtagere") scanners = models.ManyToManyField(WebScanner, blank=True, verbose_name="Scannere") organization = models.ForeignKey(Organization, null=False, verbose_name='Organisation') group = models.ForeignKey(Group, null=True, blank=True, verbose_name='Gruppe') do_email_recipients = models.BooleanField(default=False, verbose_name="Udsend mails") def __unicode__(self): """Return the name as a text representation of this summary object.""" return self.name @property def display_name(self): """Display name = name.""" return self.name class Meta: ordering = [ 'name', ]
class Events(models.Model): event_id = models.CharField(max_length=500, unique=True) created = models.DateTimeField(null=True) updated = models.DateTimeField(null=True) summary = models.CharField(max_length=1000) description = models.TextField() start_dateTime = models.DateTimeField(null=True) end_dateTime = models.DateTimeField(null=True) location = models.CharField(max_length=1000,null=True) attendees = ArrayField(models.CharField(max_length=500), blank=True,null= True) resources_used = ArrayField(models.CharField(max_length=1000), blank=True, default=[]) event_dump = JSONField(default={}) creator = models.CharField(max_length=400,blank=True,null=True) start_date = models.DateField(null=True) end_date = models.DateField(null=True) recurr = RecurrenceField(null=True) status = models.TextField(null=True) changed_dates = ArrayField(models.DateField(), blank=True, default=[]) parent_event = models.ForeignKey('self', on_delete=models.CASCADE,null=True,blank=True,to_field='event_id')
class Transaction(models.Model): budget = models.ForeignKey(Budget, on_delete=models.CASCADE) date = models.DateField() category = models.ForeignKey(Category, on_delete=models.CASCADE) account = models.ForeignKey(Account, on_delete=models.CASCADE) source = models.ForeignKey(Source, on_delete=models.CASCADE) amount = models.DecimalField(max_digits=15, decimal_places=2) note = models.CharField(max_length=150, null=True, default=None, blank=True) reconciled = models.BooleanField() recurring = models.BooleanField() recurrences = RecurrenceField() def __str__(self): return self.note def save(self, *args, **kwargs): if self.recurring == True: self.recurrences.dtstart = datetime(self.date.year, self.date.month, self.date.day, 0, 0, 0) super(Transaction, self).save(*args, **kwargs)
class RecurringNotice(models.Model): title = models.CharField(max_length=80) user = models.ForeignKey(settings.AUTH_USER_MODEL) description = models.TextField(blank=True, null=True) location = models.GeometryField() duration = models.DurationField() recurrences = RecurrenceField() created_at = models.DateTimeField(auto_now_add=True) updated_at = models.DateTimeField(auto_now=True) tags = HStoreField(blank=True, null=True) timezone = models.CharField(max_length=40, choices=_get_timezones_as_tuple(), blank=False) objects = models.GeoManager() def __str__(self): return self.title def get_absolute_url(self): return reverse('recurring-notice-detail', args=[str(self.id)])
class Agenda(models.Model): class Meta: verbose_name_plural = _("Events") verbose_name = _("Event") eventTitle = models.CharField(max_length=200, verbose_name="Title") eventCustomer = models.ForeignKey('settings.Customer', on_delete=models.CASCADE, blank=True, null=True, verbose_name="Customer") eventDescription = models.TextField(null=True, verbose_name="Description") eventStart = models.DateTimeField(verbose_name="Start at") eventEnd = models.DateTimeField(verbose_name="End at") recurrence = RecurrenceField(null=True) def publish(self): self.published_date = timezone.now() self.save() def __str__(self): return u'%s' % (self.eventTitle)
class CustomAction(models.Model): uuid = models.UUIDField(default=uuid.uuid4, editable=False, unique=True) name = models.CharField(max_length=255) description = models.TextField() owner = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE) recurrence = RecurrenceField() def get_rule(self): if self.recurrence.rrules is not None: if len(self.recurrence.rrules) > 0: return serialize(self.recurrence.rrules[0]) return None def set_rule(self, i): self.recurrence = deserialize(i) rule = property(get_rule, set_rule) created = models.DateTimeField(auto_now_add=True) modified = models.DateTimeField(auto_now=True)
class Event(models.Model): title = models.CharField(max_length=100, help_text="Title or short description of the event") description = models.TextField(blank=True, help_text="Full description of the event") recurrences = RecurrenceField(default=None, blank=True, help_text="This event occurs more than once.") start_datetime = models.DateTimeField(help_text="When does the event start?") end_datetime = models.DateTimeField(help_text="When does the event end?") organization_name = models.CharField(max_length=100, help_text="Name of the hosting organization") event_type = models.CharField(max_length=20, choices=[(t.name, t.value) for t in constants.EventType]) location = models.CharField(max_length=100, help_text="Location where the event will take place") lat = models.DecimalField(max_digits=9, decimal_places=6, null=True, blank=True, default=None) lon = models.DecimalField(max_digits=9, decimal_places=6, null=True, blank=True, default=None) is_census_equipped = models.BooleanField(default=False, help_text="Is this event technologically equipped to allow people to take the census?") approval_status = models.CharField(max_length=20, default=constants.EventApprovalStatus.PENDING.name, choices=[(t.name, t.value) for t in constants.EventApprovalStatus]) languages = MultiSelectField(choices=[(t.name, t.value) for t in constants.Languages], help_text="Add languages supported at the event") contact_name = models.CharField(max_length=100, null=True, help_text="Name of contact for event") contact_email = models.EmailField(max_length=60, null=True, help_text="Email for contact") contact_phone = PhoneNumberField(null=True, help_text="Phone number for contact") # If you need pending and active, use Event.with_pending instead of Event.objects #with_pending = models.Manager() def __str__(self): return self.title
class Event(models.Model): name = models.CharField(max_length=50) users = models.ManyToManyField('User') description = models.TextField() country = models.ForeignKey(Country, on_delete=models.CASCADE) city = models.ForeignKey(City, on_delete=models.CASCADE) created_at = models.DateTimeField(auto_now_add=True) updated_at = models.DateTimeField(auto_now=True) sport = models.ForeignKey(Sport, on_delete=models.CASCADE) datetime = models.DateTimeField() recurrences = RecurrenceField(default='') long = models.DecimalField(max_digits=12, decimal_places=7) lat = models.DecimalField(max_digits=12, decimal_places=7) difficulty = models.CharField(max_length=100) private = models.BooleanField(default=False) def __str__(self): return self.name class Meta: verbose_name_plural = 'Events' def __unicode__(self): return self.name
class Schedule(models.Model): class Meta: verbose_name = _('schedule') verbose_name_plural = _('schedules') programme = models.ForeignKey(Programme, verbose_name=_("programme")) type = models.CharField(verbose_name=_("type"), choices=EMISSION_TYPE, max_length=1) calendar = models.ForeignKey(Calendar, verbose_name=_("calendar")) recurrences = RecurrenceField(verbose_name=_("recurrences")) start_dt = models.DateTimeField(verbose_name=_('start date')) effective_start_dt = models.DateTimeField( blank=True, null=True, verbose_name=_('first effective start date'), help_text=_('This field is dynamically generated to improve performance') ) effective_end_dt = models.DateTimeField( blank=True, null=True, verbose_name=_('last effective end date'), help_text=_('This field is dynamically generated to improve performance') ) from_collection = models.ForeignKey( 'self', blank=True, null=True, on_delete=models.SET_NULL, related_name='child_schedules', help_text=_("Parent schedule (only happens when it is changed from recurrence.") ) source = models.ForeignKey( 'self', blank=True, null=True, on_delete=models.SET_NULL, verbose_name=_("source"), help_text=_("Main schedule when (if this is a broadcast).") ) def save(self, *args, **kwargs): assert self.start_dt, 'start_dt is required' self._update_recurrence_dates() # Do this every time to avoid users to delete/add exdates manually self._update_excluded_dates() self._update_effective_dates() super(Schedule, self).save(*args, **kwargs) self.programme.rearrange_episodes(timezone.now(), Calendar.get_active()) def _update_recurrence_dates(self): """ Fix for django-recurrence 1.3 We need to update the internal until datetime to include the whole day """ default_tz = timezone.get_default_timezone() for rrule in self.recurrences.rrules: if rrule.until: rrule.until = default_tz.localize(datetime.datetime.combine( transform_dt_to_default_tz(rrule.until).date(), datetime.time(23, 59, 59))) def _update_excluded_dates(self): """ We need to update dates inside ExcludedDates and the recurrence library """ exdates = [] for excluded in ExcludedDates.objects.filter(schedule=self): new_excluded_dt = excluded.get_new_excluded_datetime(self.start_dt) excluded.datetime = new_excluded_dt excluded.save() exdates.append(fix_recurrence_date(self.start_dt, new_excluded_dt)) self.recurrences.exdates = exdates def _update_effective_dates(self): # Start date has to be calculated first self.effective_start_dt = calculate_effective_schedule_start_dt(self) self.effective_end_dt = calculate_effective_schedule_end_dt(self) @property def runtime(self): return self.programme.runtime @staticmethod def get_schedule_which_excluded_dt(programme, dt): try: return ExcludedDates.objects.get(schedule__programme=programme, datetime=dt).schedule except ExcludedDates.DoesNotExist: return None def exclude_date(self, dt): local_dt = transform_dt_to_default_tz(dt) self.recurrences.exdates.append(fix_recurrence_date(self.start_dt, local_dt)) ExcludedDates.objects.create(schedule=self, datetime=dt) def include_date(self, dt): local_dt = transform_dt_to_default_tz(dt) self.recurrences.exdates.remove(fix_recurrence_date(self.start_dt, local_dt)) ExcludedDates.objects.get(schedule=self, datetime=dt).delete() def has_recurrences(self): return self.recurrences def dates_between(self, after, before): """ Return a sorted list of dates between after and before """ after_date = self._merge_after(after) if not after_date: return after_date = transform_dt_to_default_tz(after_date) before_date = transform_dt_to_default_tz(self._merge_before(before)) start_dt = transform_dt_to_default_tz(self.start_dt) # We need to send the dates in the default timezone recurrence_dates_between = self.recurrences.between(after_date, before_date, inc=True, dtstart=start_dt) # Special case to include started episodes date_before = self.date_before(after_date) if date_before and date_before < after_date < date_before + self.runtime: yield date_before # Date was already fixed for date in recurrence_dates_between: yield fix_recurrence_dst(date) # Fixing date def date_before(self, before): before_date = transform_dt_to_default_tz(self._merge_before(before)) start_dt = transform_dt_to_default_tz(self.start_dt) date = recurrence_before(self.recurrences, before_date, start_dt) return fix_recurrence_dst(date) def date_after(self, after): after_date = self._merge_after(after) if not after_date: return after_date = transform_dt_to_default_tz(after_date) start_dt = transform_dt_to_default_tz(self.start_dt) date = recurrence_after(self.recurrences, after_date, start_dt) return fix_recurrence_dst(date) def _merge_after(self, after): """ Return the greater first date taking into account the programme constraints Can return None if there is no effective_start_dt """ if not self.effective_start_dt: return None return max(after, self.effective_start_dt) def _merge_before(self, before): """ Return the smaller last date taking into account the programme constraints """ if not self.effective_end_dt: return before return min(before, self.effective_end_dt) def __unicode__(self): return ' - '.join([self.start_dt.strftime('%A'), self.start_dt.strftime('%X')])
class EventWithNulls(models.Model): recurs = RecurrenceField(null=True)