prompt: We are currently solving the following issue within our repository. Here is the issue text:
  --- BEGIN ISSUE ---
  NonExistentTimeError and AmbiguousTimeError on daylight time changes with checkin filter window
  I believe this error occurs when:
  - There is a change into or out of daylight saving time
  - A user loads a view that displays check-in statuses
  - The current time is such that the beginning of the check-in window would be during the daylight saving time transition.
  
  For example, if the check-in window is 12 hours, then loading any page that seeks check-in information (check-ins, results entry, private URL landing) at 2:15 p.m. would cause this error, because 2:15 a.m. is either ambiguous (if daylight saving just finished) or non-existent (if it just started).
  
  https://sentry.io/organizations/tabbycat-ig/issues/975799227/?project=185382&referrer=github_plugin
  
  ```
  NonExistentTimeError: 2019-04-07 02:51:30.519504
  (24 additional frame(s) were not displayed)
  ...
    File "utils/views.py", line 127, in get_tables
      return [self.get_table()]
    File "availability/views.py", line 167, in get_table
      self.annotate_checkins(queryset, self.tournament)
    File "availability/views.py", line 232, in annotate_checkins
      return get_checkins(queryset, t, 'checkin_window_people')
    File "checkins/utils.py", line 124, in get_checkins
      events = get_unexpired_checkins(t, window_preference_type).values(
    File "checkins/utils.py", line 61, in get_unexpired_checkins
      time__gte=time_window).select_related('identifier').order_by('time')
  
  NonExistentTimeError: 2019-04-07 02:51:30.519504
  ```
  
  Relates to feature originally implemented from #513.
  
  --- END ISSUE ---
  
  Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
  --- BEGIN FILES ---
  Path: `tabbycat/checkins/utils.py`
  Content:
  ```
  1 import datetime
  2 import logging
  3 import random
  4 import string
  5 
  6 from django.db import IntegrityError
  7 from django.core.exceptions import ObjectDoesNotExist
  8 from django.utils.translation import gettext as _
  9 
  10 from .models import DebateIdentifier, Event, PersonIdentifier, VenueIdentifier
  11 
  12 logger = logging.getLogger(__name__)
  13 
  14 
  15 def generate_identifier(length=6):
  16     """Generates a random identifier and saves it to the database."""
  17     chars = string.ascii_uppercase + string.digits
  18     return ''.join(random.SystemRandom().choice(chars) for _ in range(length))
  19 
  20 
  21 IDENTIFIER_CLASSES = {
  22     'participants.Person': PersonIdentifier,
  23     'draw.Debate': DebateIdentifier,
  24     'venues.Venue': VenueIdentifier,
  25 }
  26 
  27 
  28 def generate_identifiers(queryset, length=6, num_attempts=10):
  29     """Generates identifiers for every instance in the given QuerySet."""
  30     klass = IDENTIFIER_CLASSES[queryset.model._meta.label]
  31     attr = klass.instance_attr
  32 
  33     for instance in queryset:
  34         identifier = generate_identifier(length=length)
  35         for i in range(num_attempts):
  36             try:
  37                 klass.objects.create(identifier=identifier, **{attr: instance})
  38             except IntegrityError:
  39                 logger.warning("Identifier was not unique, trying again (%d of %d)", i, num_attempts)
  40                 continue
  41             else:
  42                 break
  43         else:
  44             logger.error("Could not generate unique identifier for %r after %d tries", instance, num_attempts)
  45 
  46 
  47 def delete_identifiers(queryset):
  48     klass = IDENTIFIER_CLASSES[queryset.model._meta.label]
  49     attr = klass.instance_attr
  50     klass.objects.filter(**{attr + '__in': queryset}).delete()
  51 
  52 
  53 def get_unexpired_checkins(tournament, window_preference_type):
  54     if not window_preference_type:
  55         time_window = datetime.datetime.fromtimestamp(0)  # Unix start
  56     else:
  57         start = datetime.timedelta(hours=tournament.pref(window_preference_type))
  58         time_window = datetime.datetime.now() - start
  59 
  60     events = Event.objects.filter(tournament=tournament,
  61         time__gte=time_window).select_related('identifier').order_by('time')
  62     return events
  63 
  64 
  65 def create_identifiers(model_to_make, items_to_check):
  66     kind = model_to_make.instance_attr
  67     identifiers_to_make = items_to_check.filter(checkin_identifier__isnull=True)
  68 
  69     for item in identifiers_to_make:
  70         model_to_make.objects.create(**{kind: item})
  71 
  72     return
  73 
  74 
  75 def single_checkin(instance, events):
  76     instance.checked_icon = ''
  77     instance.checked_in = False
  78     try:
  79         identifier = instance.checkin_identifier
  80         instance.barcode = identifier.barcode
  81         instance.checked_tooltip = _("Not checked in (barcode %(barcode)s)") % {'barcode': identifier.barcode}
  82     except ObjectDoesNotExist:
  83         identifier = None
  84         instance.barcode = None
  85         instance.checked_tooltip = _("Not checked in; no barcode assigned")
  86 
  87     if identifier:
  88         instance.time = next((e['time'] for e in events if e['identifier__barcode'] == identifier.barcode), None)
  89         if instance.time:
  90             instance.checked_in = True
  91             instance.checked_icon = 'check'
  92             instance.checked_tooltip = _("checked in at %(time)s") % {'time': instance.time.strftime('%H:%M')}
  93     return instance
  94 
  95 
  96 def multi_checkin(team, events, t):
  97     team.checked_icon = ''
  98     team.checked_in = False
  99     tooltips = []
  100 
  101     for speaker in team.speaker_set.all():
  102         speaker = single_checkin(speaker, events)
  103         if speaker.checked_in:
  104             tooltip = _("%(speaker)s checked in at %(time)s.") % {'speaker': speaker.name, 'time': speaker.time.strftime('%H:%M')}
  105         else:
  106             tooltip = _("%(speaker)s is missing.") % {'speaker': speaker.name}
  107         tooltips.append(tooltip)
  108 
  109     team.checked_tooltip = " ".join(tooltips)
  110 
  111     check_ins = sum(s.checked_in for s in team.speaker_set.all())
  112     nsubstantives = t.pref('substantive_speakers')
  113     if check_ins >= nsubstantives:
  114         team.checked_in = True
  115         team.checked_icon = 'check'
  116     elif check_ins == nsubstantives - 1:
  117         team.checked_in = True
  118         team.checked_icon = 'shuffle'
  119 
  120     return team
  121 
  122 
  123 def get_checkins(queryset, t, window_preference_type):
  124     events = get_unexpired_checkins(t, window_preference_type).values(
  125         'time', 'identifier__barcode')
  126     for instance in queryset:
  127         if hasattr(instance, 'use_institution_prefix'):
  128             instance = multi_checkin(instance, events, t)
  129         else:
  130             instance = single_checkin(instance, events)
  131 
  132     return queryset
  133
  ```
  --- END FILES ---
  
  Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.
  
  Here is an example:
  
  ```diff
  diff --git a/examples/server_async.py b/examples/server_async.py
  --- a/examples/server_async.py
  +++ b/examples/server_async.py
  @@ -313,4 +313,4 @@
   
   
   if __name__ == "__main__":
  -    asyncio.run(run_async_server("."), debug=True)
  +    asyncio.run(run_async_server(), debug=True)
  diff --git a/examples/server_sync.py b/examples/server_sync.py
  --- a/examples/server_sync.py
  +++ b/examples/server_sync.py
  @@ -313,5 +313,5 @@
   
   
   if __name__ == "__main__":
  -    server = run_sync_server(".")
  +    server = run_sync_server()
       server.shutdown()
  
  ```
  
golden_diff: diff --git a/tabbycat/checkins/utils.py b/tabbycat/checkins/utils.py
  --- a/tabbycat/checkins/utils.py
  +++ b/tabbycat/checkins/utils.py
  @@ -4,7 +4,9 @@
   import string
   
   from django.db import IntegrityError
  +from django.db.models import Q
   from django.core.exceptions import ObjectDoesNotExist
  +from django.utils import timezone
   from django.utils.translation import gettext as _
   
   from .models import DebateIdentifier, Event, PersonIdentifier, VenueIdentifier
  @@ -51,15 +53,13 @@
   
   
   def get_unexpired_checkins(tournament, window_preference_type):
  -    if not window_preference_type:
  -        time_window = datetime.datetime.fromtimestamp(0)  # Unix start
  -    else:
  +    filters = Q(tournament=tournament)
  +    if window_preference_type:
           start = datetime.timedelta(hours=tournament.pref(window_preference_type))
  -        time_window = datetime.datetime.now() - start
  +        time_window = timezone.now() - start
  +        filters &= Q(time_gte=time_window)
   
  -    events = Event.objects.filter(tournament=tournament,
  -        time__gte=time_window).select_related('identifier').order_by('time')
  -    return events
  +    return Event.objects.filter(filters).select_related('identifier').order_by('time')
   
   
   def create_identifiers(model_to_make, items_to_check):
  
verification_info: {"golden_diff": "diff --git a/tabbycat/checkins/utils.py b/tabbycat/checkins/utils.py\n--- a/tabbycat/checkins/utils.py\n+++ b/tabbycat/checkins/utils.py\n@@ -4,7 +4,9 @@\n import string\n \n from django.db import IntegrityError\n+from django.db.models import Q\n from django.core.exceptions import ObjectDoesNotExist\n+from django.utils import timezone\n from django.utils.translation import gettext as _\n \n from .models import DebateIdentifier, Event, PersonIdentifier, VenueIdentifier\n@@ -51,15 +53,13 @@\n \n \n def get_unexpired_checkins(tournament, window_preference_type):\n-    if not window_preference_type:\n-        time_window = datetime.datetime.fromtimestamp(0)  # Unix start\n-    else:\n+    filters = Q(tournament=tournament)\n+    if window_preference_type:\n         start = datetime.timedelta(hours=tournament.pref(window_preference_type))\n-        time_window = datetime.datetime.now() - start\n+        time_window = timezone.now() - start\n+        filters &= Q(time_gte=time_window)\n \n-    events = Event.objects.filter(tournament=tournament,\n-        time__gte=time_window).select_related('identifier').order_by('time')\n-    return events\n+    return Event.objects.filter(filters).select_related('identifier').order_by('time')\n \n \n def create_identifiers(model_to_make, items_to_check):\n", "issue": "NonExistentTimeError and AmbiguousTimeError on daylight time changes with checkin filter window\nI believe this error occurs when:\n- There is a change into or out of daylight saving time\n- A user loads a view that displays check-in statuses\n- The current time is such that the beginning of the check-in window would be during the daylight saving time transition.\n\nFor example, if the check-in window is 12 hours, then loading any page that seeks check-in information (check-ins, results entry, private URL landing) at 2:15 p.m. would cause this error, because 2:15 a.m. is either ambiguous (if daylight saving just finished) or non-existent (if it just started).\n\nhttps://sentry.io/organizations/tabbycat-ig/issues/975799227/?project=185382&referrer=github_plugin\n\n```\nNonExistentTimeError: 2019-04-07 02:51:30.519504\n(24 additional frame(s) were not displayed)\n...\n  File \"utils/views.py\", line 127, in get_tables\n    return [self.get_table()]\n  File \"availability/views.py\", line 167, in get_table\n    self.annotate_checkins(queryset, self.tournament)\n  File \"availability/views.py\", line 232, in annotate_checkins\n    return get_checkins(queryset, t, 'checkin_window_people')\n  File \"checkins/utils.py\", line 124, in get_checkins\n    events = get_unexpired_checkins(t, window_preference_type).values(\n  File \"checkins/utils.py\", line 61, in get_unexpired_checkins\n    time__gte=time_window).select_related('identifier').order_by('time')\n\nNonExistentTimeError: 2019-04-07 02:51:30.519504\n```\n\nRelates to feature originally implemented from #513.\n", "before_files": [{"content": "import datetime\nimport logging\nimport random\nimport string\n\nfrom django.db import IntegrityError\nfrom django.core.exceptions import ObjectDoesNotExist\nfrom django.utils.translation import gettext as _\n\nfrom .models import DebateIdentifier, Event, PersonIdentifier, VenueIdentifier\n\nlogger = logging.getLogger(__name__)\n\n\ndef generate_identifier(length=6):\n    \"\"\"Generates a random identifier and saves it to the database.\"\"\"\n    chars = string.ascii_uppercase + string.digits\n    return ''.join(random.SystemRandom().choice(chars) for _ in range(length))\n\n\nIDENTIFIER_CLASSES = {\n    'participants.Person': PersonIdentifier,\n    'draw.Debate': DebateIdentifier,\n    'venues.Venue': VenueIdentifier,\n}\n\n\ndef generate_identifiers(queryset, length=6, num_attempts=10):\n    \"\"\"Generates identifiers for every instance in the given QuerySet.\"\"\"\n    klass = IDENTIFIER_CLASSES[queryset.model._meta.label]\n    attr = klass.instance_attr\n\n    for instance in queryset:\n        identifier = generate_identifier(length=length)\n        for i in range(num_attempts):\n            try:\n                klass.objects.create(identifier=identifier, **{attr: instance})\n            except IntegrityError:\n                logger.warning(\"Identifier was not unique, trying again (%d of %d)\", i, num_attempts)\n                continue\n            else:\n                break\n        else:\n            logger.error(\"Could not generate unique identifier for %r after %d tries\", instance, num_attempts)\n\n\ndef delete_identifiers(queryset):\n    klass = IDENTIFIER_CLASSES[queryset.model._meta.label]\n    attr = klass.instance_attr\n    klass.objects.filter(**{attr + '__in': queryset}).delete()\n\n\ndef get_unexpired_checkins(tournament, window_preference_type):\n    if not window_preference_type:\n        time_window = datetime.datetime.fromtimestamp(0)  # Unix start\n    else:\n        start = datetime.timedelta(hours=tournament.pref(window_preference_type))\n        time_window = datetime.datetime.now() - start\n\n    events = Event.objects.filter(tournament=tournament,\n        time__gte=time_window).select_related('identifier').order_by('time')\n    return events\n\n\ndef create_identifiers(model_to_make, items_to_check):\n    kind = model_to_make.instance_attr\n    identifiers_to_make = items_to_check.filter(checkin_identifier__isnull=True)\n\n    for item in identifiers_to_make:\n        model_to_make.objects.create(**{kind: item})\n\n    return\n\n\ndef single_checkin(instance, events):\n    instance.checked_icon = ''\n    instance.checked_in = False\n    try:\n        identifier = instance.checkin_identifier\n        instance.barcode = identifier.barcode\n        instance.checked_tooltip = _(\"Not checked in (barcode %(barcode)s)\") % {'barcode': identifier.barcode}\n    except ObjectDoesNotExist:\n        identifier = None\n        instance.barcode = None\n        instance.checked_tooltip = _(\"Not checked in; no barcode assigned\")\n\n    if identifier:\n        instance.time = next((e['time'] for e in events if e['identifier__barcode'] == identifier.barcode), None)\n        if instance.time:\n            instance.checked_in = True\n            instance.checked_icon = 'check'\n            instance.checked_tooltip = _(\"checked in at %(time)s\") % {'time': instance.time.strftime('%H:%M')}\n    return instance\n\n\ndef multi_checkin(team, events, t):\n    team.checked_icon = ''\n    team.checked_in = False\n    tooltips = []\n\n    for speaker in team.speaker_set.all():\n        speaker = single_checkin(speaker, events)\n        if speaker.checked_in:\n            tooltip = _(\"%(speaker)s checked in at %(time)s.\") % {'speaker': speaker.name, 'time': speaker.time.strftime('%H:%M')}\n        else:\n            tooltip = _(\"%(speaker)s is missing.\") % {'speaker': speaker.name}\n        tooltips.append(tooltip)\n\n    team.checked_tooltip = \" \".join(tooltips)\n\n    check_ins = sum(s.checked_in for s in team.speaker_set.all())\n    nsubstantives = t.pref('substantive_speakers')\n    if check_ins >= nsubstantives:\n        team.checked_in = True\n        team.checked_icon = 'check'\n    elif check_ins == nsubstantives - 1:\n        team.checked_in = True\n        team.checked_icon = 'shuffle'\n\n    return team\n\n\ndef get_checkins(queryset, t, window_preference_type):\n    events = get_unexpired_checkins(t, window_preference_type).values(\n        'time', 'identifier__barcode')\n    for instance in queryset:\n        if hasattr(instance, 'use_institution_prefix'):\n            instance = multi_checkin(instance, events, t)\n        else:\n            instance = single_checkin(instance, events)\n\n    return queryset\n", "path": "tabbycat/checkins/utils.py"}], "after_files": [{"content": "import datetime\nimport logging\nimport random\nimport string\n\nfrom django.db import IntegrityError\nfrom django.db.models import Q\nfrom django.core.exceptions import ObjectDoesNotExist\nfrom django.utils import timezone\nfrom django.utils.translation import gettext as _\n\nfrom .models import DebateIdentifier, Event, PersonIdentifier, VenueIdentifier\n\nlogger = logging.getLogger(__name__)\n\n\ndef generate_identifier(length=6):\n    \"\"\"Generates a random identifier and saves it to the database.\"\"\"\n    chars = string.ascii_uppercase + string.digits\n    return ''.join(random.SystemRandom().choice(chars) for _ in range(length))\n\n\nIDENTIFIER_CLASSES = {\n    'participants.Person': PersonIdentifier,\n    'draw.Debate': DebateIdentifier,\n    'venues.Venue': VenueIdentifier,\n}\n\n\ndef generate_identifiers(queryset, length=6, num_attempts=10):\n    \"\"\"Generates identifiers for every instance in the given QuerySet.\"\"\"\n    klass = IDENTIFIER_CLASSES[queryset.model._meta.label]\n    attr = klass.instance_attr\n\n    for instance in queryset:\n        identifier = generate_identifier(length=length)\n        for i in range(num_attempts):\n            try:\n                klass.objects.create(identifier=identifier, **{attr: instance})\n            except IntegrityError:\n                logger.warning(\"Identifier was not unique, trying again (%d of %d)\", i, num_attempts)\n                continue\n            else:\n                break\n        else:\n            logger.error(\"Could not generate unique identifier for %r after %d tries\", instance, num_attempts)\n\n\ndef delete_identifiers(queryset):\n    klass = IDENTIFIER_CLASSES[queryset.model._meta.label]\n    attr = klass.instance_attr\n    klass.objects.filter(**{attr + '__in': queryset}).delete()\n\n\ndef get_unexpired_checkins(tournament, window_preference_type):\n    filters = Q(tournament=tournament)\n    if window_preference_type:\n        start = datetime.timedelta(hours=tournament.pref(window_preference_type))\n        time_window = timezone.now() - start\n        filters &= Q(time_gte=time_window)\n\n    return Event.objects.filter(filters).select_related('identifier').order_by('time')\n\n\ndef create_identifiers(model_to_make, items_to_check):\n    kind = model_to_make.instance_attr\n    identifiers_to_make = items_to_check.filter(checkin_identifier__isnull=True)\n\n    for item in identifiers_to_make:\n        model_to_make.objects.create(**{kind: item})\n\n    return\n\n\ndef single_checkin(instance, events):\n    instance.checked_icon = ''\n    instance.checked_in = False\n    try:\n        identifier = instance.checkin_identifier\n        instance.barcode = identifier.barcode\n        instance.checked_tooltip = _(\"Not checked in (barcode %(barcode)s)\") % {'barcode': identifier.barcode}\n    except ObjectDoesNotExist:\n        identifier = None\n        instance.barcode = None\n        instance.checked_tooltip = _(\"Not checked in; no barcode assigned\")\n\n    if identifier:\n        instance.time = next((e['time'] for e in events if e['identifier__barcode'] == identifier.barcode), None)\n        if instance.time:\n            instance.checked_in = True\n            instance.checked_icon = 'check'\n            instance.checked_tooltip = _(\"checked in at %(time)s\") % {'time': instance.time.strftime('%H:%M')}\n    return instance\n\n\ndef multi_checkin(team, events, t):\n    team.checked_icon = ''\n    team.checked_in = False\n    tooltips = []\n\n    for speaker in team.speaker_set.all():\n        speaker = single_checkin(speaker, events)\n        if speaker.checked_in:\n            tooltip = _(\"%(speaker)s checked in at %(time)s.\") % {'speaker': speaker.name, 'time': speaker.time.strftime('%H:%M')}\n        else:\n            tooltip = _(\"%(speaker)s is missing.\") % {'speaker': speaker.name}\n        tooltips.append(tooltip)\n\n    team.checked_tooltip = \" \".join(tooltips)\n\n    check_ins = sum(s.checked_in for s in team.speaker_set.all())\n    nsubstantives = t.pref('substantive_speakers')\n    if check_ins >= nsubstantives:\n        team.checked_in = True\n        team.checked_icon = 'check'\n    elif check_ins == nsubstantives - 1:\n        team.checked_in = True\n        team.checked_icon = 'shuffle'\n\n    return team\n\n\ndef get_checkins(queryset, t, window_preference_type):\n    events = get_unexpired_checkins(t, window_preference_type).values(\n        'time', 'identifier__barcode')\n    for instance in queryset:\n        if hasattr(instance, 'use_institution_prefix'):\n            instance = multi_checkin(instance, events, t)\n        else:\n            instance = single_checkin(instance, events)\n\n    return queryset\n", "path": "tabbycat/checkins/utils.py"}]}