Skip to content

Commit

Permalink
Add basic queue to show decisions where action has been held
Browse files Browse the repository at this point in the history
  • Loading branch information
eviljeff committed Oct 21, 2024
1 parent db59c02 commit 61382de
Show file tree
Hide file tree
Showing 8 changed files with 100 additions and 26 deletions.
28 changes: 4 additions & 24 deletions src/olympia/abuse/actions.py
Original file line number Diff line number Diff line change
Expand Up @@ -83,26 +83,6 @@ def get_owners(self):
"""No owner emails will be sent. Override to send owner emails"""
return ()

def get_target_name(self):
return str(
_('"{}" for {}').format(self.target, self.target.addon.name)
if isinstance(self.target, Rating)
else getattr(self.target, 'name', self.target)
)

def get_target_type(self):
match self.target:
case target if isinstance(target, Addon):
return target.get_type_display()
case target if isinstance(target, UserProfile):
return _('User profile')
case target if isinstance(target, Collection):
return _('Collection')
case target if isinstance(target, Rating):
return _('Rating')
case target:
return target.__class__.__name__

@property
def owner_template_path(self):
return f'abuse/emails/{self.__class__.__name__}.txt'
Expand All @@ -114,7 +94,7 @@ def notify_owners(self, *, log_entry_id=None, extra_context=None):
if not owners:
return
template = loader.get_template(self.owner_template_path)
target_name = self.get_target_name()
target_name = self.decision.get_target_name()
reference_id = f'ref:{self.decision.get_reference_id()}'
# override target_url to devhub if there is no public listing
target_url = (
Expand All @@ -134,7 +114,7 @@ def notify_owners(self, *, log_entry_id=None, extra_context=None):
'reference_id': reference_id,
'target': self.target,
'target_url': target_url,
'type': self.get_target_type(),
'type': self.decision.get_target_type(),
'SITE_URL': settings.SITE_URL,
**(extra_context or {}),
}
Expand Down Expand Up @@ -194,7 +174,7 @@ def notify_reporters(self, *, reporter_abuse_reports, is_appeal=False):
with translation.override(
abuse_report.application_locale or settings.LANGUAGE_CODE
):
target_name = self.get_target_name()
target_name = self.decision.get_target_name()
reference_id = (
f'ref:{self.decision.get_reference_id()}/{abuse_report.id}'
)
Expand All @@ -209,7 +189,7 @@ def notify_reporters(self, *, reporter_abuse_reports, is_appeal=False):
'policy_document_url': POLICY_DOCUMENT_URL,
'reference_id': reference_id,
'target_url': absolutify(self.target.get_url_path()),
'type': self.get_target_type(),
'type': self.decision.get_target_type(),
'SITE_URL': settings.SITE_URL,
}
if is_appeal:
Expand Down
29 changes: 29 additions & 0 deletions src/olympia/abuse/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@
from django.db import models
from django.db.models import Exists, OuterRef, Q
from django.db.transaction import atomic
from django.urls import reverse
from django.utils.functional import cached_property
from django.utils.translation import gettext_lazy as _

from olympia import amo
from olympia.addons.models import Addon
Expand Down Expand Up @@ -1265,6 +1267,33 @@ def process_action(self, overridden_action=None):
else:
action_helper.hold_action()

def get_target_review_url(self):
return (
reverse('reviewers.review', args=(self.target.id,))
if isinstance(self.target, Addon)
else ''
)

def get_target_type(self):
match self.target:
case target if isinstance(target, Addon):
return target.get_type_display()
case target if isinstance(target, UserProfile):
return _('User profile')
case target if isinstance(target, Collection):
return _('Collection')
case target if isinstance(target, Rating):
return _('Rating')
case target:
return target.__class__.__name__

def get_target_name(self):
return str(
_('"{}" for {}').format(self.target, self.target.addon.name)
if isinstance(self.target, Rating)
else getattr(self.target, 'name', self.target)
)


class CinderAppeal(ModelBase):
text = models.TextField(blank=False, help_text='The content of the appeal.')
Expand Down
24 changes: 24 additions & 0 deletions src/olympia/reviewers/templates/reviewers/queue.html
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,30 @@ <h3>
{% endif %}
</form>
</div>
{% elif tab == 'held_actions' %}
<table id="action-queue" class="data-grid">
<thead>
<tr class="listing-header">
<th>Type</th>
<th>Target</th>
<th>Action</th>
<th>Decision Date</th>
</tr>
</thead>
<tbody>
{% for decision in page.object_list %}
<tr id="{{ decision.get_reference_id(short=True) }}">
<td><div class="app-icon ed-sprite-action-target-{{ decision.get_target_type() }}" title="{{ decision.get_target_type() }}"></div></td>
<td>{{ decision.get_target_name() }}</td>
<td><a href="{{ decision.get_target_review_url() }}">{{ decision.get_action_display() }}</a></td>
<td>{{ decision.created|datetime }}</td>
</tr>
{% endfor %}
</tbody>
</table>
{% if page.paginator.count == 0 %}
<div class="no-results">There are currently no held actions.</div>
{% endif %}
{% else %}
<div id="addon-queue-filter-form">
<button class="show-hide-toggle">Show/Hide Filter Selections</button>
Expand Down
1 change: 1 addition & 0 deletions src/olympia/reviewers/templatetags/jinja_helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ def queue_tabnav(context, reviewer_tables_registry):
'moderated',
'content_review',
'pending_rejection',
'held_actions',
):
if acl.action_allowed_for(
request.user, reviewer_tables_registry[queue].permission
Expand Down
16 changes: 14 additions & 2 deletions src/olympia/reviewers/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@

import olympia.core.logger
from olympia import amo
from olympia.abuse.models import CinderJob, CinderPolicy
from olympia.abuse.models import CinderJob, CinderPolicy, ContentDecision
from olympia.abuse.tasks import notify_addon_decision_to_cinder, resolve_job_in_cinder
from olympia.access import acl
from olympia.activity.models import ActivityLog, AttachmentLog
Expand Down Expand Up @@ -295,6 +295,18 @@ class ModerationQueueTable:
view_name = 'queue_moderated'


class HeldActionQueueTable:
title = 'Held Actions 2nd Level Approvals'
urlname = 'queue_held_actions'
url = r'^held_actions$'
permission = amo.permissions.REVIEWS_ADMIN
show_count_in_dashboard = False
view_name = 'queue_held_actions'

@classmethod
def get_queryset(cls, request, **kw):
return ContentDecision.objects.filter(action_date=None)

class ReviewHelper:
"""
A class that builds enough to render the form back to the user and
Expand Down Expand Up @@ -1075,7 +1087,7 @@ def resolve_appeal_job(self):
for job in self.data.get('cinder_jobs_to_resolve', ()):
# collect all the policies we made decisions under
previous_policies = CinderPolicy.objects.filter(
cinderdecision__appeal_job=job
contentdecision__appeal_job=job
).distinct()
# we just need a single action for this appeal
# - use min() to favor AMO_DISABLE_ADDON over AMO_REJECT_VERSION_ADDON
Expand Down
21 changes: 21 additions & 0 deletions src/olympia/reviewers/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,7 @@
)
from olympia.reviewers.utils import (
ContentReviewTable,
HeldActionQueueTable,
MadReviewTable,
ModerationQueueTable,
PendingManualApprovalQueueTable,
Expand Down Expand Up @@ -210,6 +211,7 @@ def dashboard(request):
reverse('reviewers.queue_extension'),
),
('Review Log', reverse('reviewers.reviewlog')),
('Held actions 2nd level review', reverse('reviewers.queue_held_actions')),
(
'Add-on Review Guide',
'https://wiki.mozilla.org/Add-ons/Reviewers/Guide',
Expand Down Expand Up @@ -431,6 +433,7 @@ def queue_moderated(request, tab):
'mad': MadReviewTable,
'pending_rejection': PendingRejectionTable,
'moderated': ModerationQueueTable,
'held_actions': HeldActionQueueTable,
}


Expand Down Expand Up @@ -1578,3 +1581,21 @@ def index_in_versions_list(channel, value):
)
url = reverse('reviewers.review', args=(channel_text, addon.pk))
return redirect(url + page_param + f'#version-{to_dom_id(version)}')


@permission_or_tools_listed_view_required(amo.permissions.REVIEWS_ADMIN)
def queue_held_actions(request, tab):
TableObj = reviewer_tables_registry[tab]
qs = TableObj.get_queryset(request)
page = paginate(request, qs, per_page=20)

return TemplateResponse(
request,
'reviewers/queue.html',
context=context(
tab=tab,
page=page,
registry=reviewer_tables_registry,
title=TableObj.title,
),
)
7 changes: 7 additions & 0 deletions static/css/zamboni/reviewers.less
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,13 @@
.ed-sprite-needs-human-review-from-cinder { background-position: 0 -484px; }
.ed-sprite-needs-human-review-from-appeal { background-position: 0 -500px; }

.ed-sprite-action-target-Extension { background-position: 0 -532px; }
.ed-sprite-action-target-Theme { background-position: 0 -564px; }
.ed-sprite-action-target-Collection { background-position: 0 -548px; }
.ed-sprite-action-target-Rating { background-position: 0 -112px; }
.ed-sprite-action-target-User { background-position: 0 -516px; }


.platform-icon {
background: url(../../img/developers/platforms.png?8) no-repeat top left;
}
Expand Down
Binary file modified static/img/developers/reviewer-sprite.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.

0 comments on commit 61382de

Please sign in to comment.