Example #1
0
    def update_judgement_queues(self):
        def _compute_queue(judge: User):
            days = settings.IOTD_JUDGEMENT_WINDOW_DAYS
            cutoff = datetime.now() - timedelta(days)

            return Image.objects.annotate(
                num_votes=Count('iotdvote', distinct=True),
                num_dismissals=Count('iotddismissedimage', distinct=True),
                last_vote_timestamp=Subquery(IotdVote.last_for_image(OuterRef('pk')).values('date'))
            ).filter(
                Q(deleted__isnull=True) &
                Q(last_vote_timestamp__gte=cutoff) &
                Q(num_votes__gte=settings.IOTD_REVIEW_MIN_PROMOTIONS) &
                Q(num_dismissals__lt=settings.IOTD_MAX_DISMISSALS) &
                Q(
                    Q(iotd__isnull=True) |
                    Q(iotd__date__gt=datetime.now().date())
                )
            ).exclude(
                Q(iotdvote__reviewer=judge) |
                Q(iotddismissedimage__user=judge) |
                Q(user=judge)
            )

        for judge in User.objects.filter(groups__name='iotd_judges'):
            IotdJudgementQueueEntry.objects.filter(judge=judge).delete()
            for image in _compute_queue(judge).iterator():
                last_vote = IotdVote.last_for_image(image.pk).first()
                IotdJudgementQueueEntry.objects.create(
                    judge=judge,
                    image=image,
                    last_vote_timestamp=last_vote.date
                )
    def to_representation(self, instance: Image):
        representation = super().to_representation(instance)
        last_vote: QuerySet[IotdVote] = IotdVote.last_for_image(instance.pk)

        if last_vote:
            representation.update(
                {
                    'last_vote_timestamp': last_vote[0].date if last_vote.exists() else None
                }
            )

        return representation
Example #3
0
        def _compute_queue(judge: User):
            days = settings.IOTD_JUDGEMENT_WINDOW_DAYS
            cutoff = datetime.now() - timedelta(days)

            return Image.objects.annotate(
                num_votes=Count('iotdvote', distinct=True),
                num_dismissals=Count('iotddismissedimage', distinct=True),
                last_vote_timestamp=Subquery(IotdVote.last_for_image(OuterRef('pk')).values('date'))
            ).filter(
                Q(deleted__isnull=True) &
                Q(last_vote_timestamp__gte=cutoff) &
                Q(num_votes__gte=settings.IOTD_REVIEW_MIN_PROMOTIONS) &
                Q(num_dismissals__lt=settings.IOTD_MAX_DISMISSALS) &
                Q(
                    Q(iotd__isnull=True) |
                    Q(iotd__date__gt=datetime.now().date())
                )
            ).exclude(
                Q(iotdvote__reviewer=judge) |
                Q(iotddismissedimage__user=judge) |
                Q(user=judge)
            )
Example #4
0
def may_elect_iotd(user, image):
    if not user.groups.filter(name='iotd_judges').exists():
        return False, _("You are not a member of the IOTD Judges board.")

    if user == image.user:
        return False, _("You cannot elect your own image.")

    if image.is_wip:
        return False, _("Images in the staging area cannot be elected.")

    if image.user.userprofile.exclude_from_competitions:
        return False, _(
            "This user has chosen to be excluded from competitions.")

    if image.user.userprofile.banned_from_competitions:
        return False, _("This user has been banned from competitions.")

    from astrobin_apps_iotd.models import IotdDismissedImage

    if IotdDismissedImage.objects.filter(
            image=image).count() >= settings.IOTD_MAX_DISMISSALS:
        return False, _(
            "You cannot submit an image that has been dismissed by %(number)s member(s) of the IOTD Staff."
        ) % {
            'number': settings.IOTD_MAX_DISMISSALS
        }

    if settings.PREMIUM_RESTRICTS_IOTD:
        if is_free(image.user):
            return False, _(
                "Users with a Free membership cannot participate in the IOTD.")

    # Import here to avoid circular dependency
    from astrobin_apps_iotd.models import IotdSubmission, IotdVote, Iotd

    if not IotdVote.objects.filter(image=image).exists():
        return False, _("You cannot elect an image that has not been voted.")

    if user.pk in IotdSubmission.objects.filter(image=image).values_list(
            'submitter', flat=True):
        return False, _("You cannot elect your own submission.")

    if user.pk in IotdVote.objects.filter(image=image).values_list('reviewer',
                                                                   flat=True):
        return False, _("You cannot elect an image you voted for.")

    if Iotd.objects.filter(image=image,
                           date__lte=datetime.now().date()).exists():
        return False, _("This image has already been an IOTD in the past")

    days = settings.IOTD_JUDGEMENT_WINDOW_DAYS
    if IotdVote.last_for_image(
            image.pk)[0].date < datetime.now() - timedelta(days):
        return False, _(
            "You cannot elect an image that has been in the review queue for more than %(max_days)s day(s)."
        ) % {
            'max_days': days
        }

    max_allowed = settings.IOTD_JUDGEMENT_MAX_PER_DAY
    judged_today = Iotd.objects.filter(
        judge=user, created__contains=datetime.now().date()).count()
    toggling_on = not Iotd.objects.filter(image=image).exists()
    if judged_today >= max_allowed and toggling_on:
        return False, _(
            "You have already elected %(max_allowed)s image(s) today.") % {
                'max_allowed': max_allowed
            }

    max_allowed = settings.IOTD_JUDGEMENT_MAX_FUTURE_PER_JUDGE
    scheduled = Iotd.objects.filter(judge=user,
                                    date__gt=datetime.now().date()).count()
    toggling_on = not Iotd.objects.filter(image=image).exists()
    if scheduled >= max_allowed and toggling_on:
        return False, _(
            "You have already scheduled %(max_allowed)s IOTD(s).") % {
                'max_allowed': max_allowed
            }

    if IotdVote.objects.filter(
            image=image).count() < settings.IOTD_REVIEW_MIN_PROMOTIONS:
        return False, _(
            "You cannot elect for an image that has not been voted at least %(num)s times."
            % {'num': settings.IOTD_REVIEW_MIN_PROMOTIONS})

    return True, None
Example #5
0
def may_elect_iotd(user, image):
    if user.is_superuser:
        return True, None

    if not user.groups.filter(name = 'iotd_judges').exists():
        return False, _("You are not a member of the IOTD Judges board.")

    if user == image.user:
        return False, _("You cannot elect your own image.")

    if image.is_wip:
        return False, _("Images in the staging area cannot be elected.")

    if image.user.userprofile.exclude_from_competitions:
        return False, _("This user has chosen to be excluded from competitions.")

    if image.user in Group.objects.get(name = 'iotd_judges').user_set.all():
        return False, _("You cannot elect a judge's image.")

    # Import here to avoid circular dependency
    from astrobin_apps_iotd.models import IotdSubmission, IotdVote, Iotd

    if not IotdVote.objects.filter(image = image).exists():
        return False, _("You cannot elect an image that has not been voted.")

    if user.pk in IotdSubmission.objects.filter(image = image).values_list('submitter', flat = True):
        return False, _("You cannot elect your own submission.")

    if user.pk in IotdVote.objects.filter(image = image).values_list('reviewer', flat = True):
        return False, _("You cannot elect an image you voted for.")

    if Iotd.objects.filter(image = image, date__lte = datetime.now().date()).exists():
        return False, _("This image has already been an IOTD in the past")

    days = settings.IOTD_JUDGEMENT_WINDOW_DAYS
    if IotdVote.first_for_image(image).date < datetime.now() - timedelta(days):
        return False, _("You cannot elect an image that has been in the review queue for more than %(max_days)s days.") % {
            'max_days': days
        }

    max_allowed = settings.IOTD_JUDGEMENT_MAX_PER_DAY
    judged_today = Iotd.objects.filter(
        judge = user,
        created__contains = datetime.now().date()).count()
    toggling_on = not Iotd.objects.filter(image = image).exists()
    if judged_today >= max_allowed and toggling_on:
        return False, _("You have already elected %(max_allowed)s images today.") % {
            'max_allowed': max_allowed
        }

    max_allowed = settings.IOTD_JUDGEMENT_MAX_FUTURE_PER_JUDGE
    scheduled = Iotd.objects.filter(
        judge = user,
        date__gt = datetime.now().date()).count()
    toggling_on = not Iotd.objects.filter(image = image).exists()
    if scheduled >= max_allowed and toggling_on:
        return False, _("You have already scheduled %(max_allowed)s IOTDs.") % {
            'max_allowed': max_allowed
        }

    return True, None
Example #6
0
def may_elect_iotd(user, image):
    if user.is_superuser:
        return True, None

    if not user.groups.filter(name='iotd_judges').exists():
        return False, _("You are not a member of the IOTD Judges board.")

    if user == image.user:
        return False, _("You cannot elect your own image.")

    if image.is_wip:
        return False, _("Images in the staging area cannot be elected.")

    if image.user.userprofile.exclude_from_competitions:
        return False, _(
            "This user has chosen to be excluded from competitions.")

    if image.user in Group.objects.get(name='iotd_judges').user_set.all():
        return False, _("You cannot elect a judge's image.")

    # Import here to avoid circular dependency
    from astrobin_apps_iotd.models import IotdSubmission, IotdVote, Iotd

    if not IotdVote.objects.filter(image=image).exists():
        return False, _("You cannot elect an image that has not been voted.")

    if user.pk in IotdSubmission.objects.filter(image=image).values_list(
            'submitter', flat=True):
        return False, _("You cannot elect your own submission.")

    if user.pk in IotdVote.objects.filter(image=image).values_list('reviewer',
                                                                   flat=True):
        return False, _("You cannot elect an image you voted for.")

    if Iotd.objects.filter(image=image,
                           date__lte=datetime.now().date()).exists():
        return False, _("This image has already been an IOTD in the past")

    days = settings.IOTD_JUDGEMENT_WINDOW_DAYS
    if IotdVote.first_for_image(image).date < datetime.now() - timedelta(days):
        return False, _(
            "You cannot elect an image that has been in the review queue for more than %(max_days)s days."
        ) % {
            'max_days': days
        }

    max_allowed = settings.IOTD_JUDGEMENT_MAX_PER_DAY
    judged_today = Iotd.objects.filter(
        judge=user, created__contains=datetime.now().date()).count()
    toggling_on = not Iotd.objects.filter(image=image).exists()
    if judged_today >= max_allowed and toggling_on:
        return False, _(
            "You have already elected %(max_allowed)s images today.") % {
                'max_allowed': max_allowed
            }

    max_allowed = settings.IOTD_JUDGEMENT_MAX_FUTURE_PER_JUDGE
    scheduled = Iotd.objects.filter(judge=user,
                                    date__gt=datetime.now().date()).count()
    toggling_on = not Iotd.objects.filter(image=image).exists()
    if scheduled >= max_allowed and toggling_on:
        return False, _(
            "You have already scheduled %(max_allowed)s IOTDs.") % {
                'max_allowed': max_allowed
            }

    return True, None