Skip to content

Commit 8f5d0f3

Browse files
authored
feat: Allow users to report comments (#3016)
Comments can be used to potentially harass users who request comments. A button was added to report a message as inappropriate. Resolves #2715
1 parent b7fd473 commit 8f5d0f3

33 files changed

+416
-103
lines changed

app/assets/stylesheets/request-for-comments.css.scss

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -212,6 +212,10 @@ html[data-bs-theme="light"] {
212212
button {
213213
margin-right: 5px;
214214
}
215+
216+
.action-report {
217+
margin-left: auto;
218+
}
215219
}
216220
}
217221
}

app/controllers/comments_controller.rb

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
# frozen_string_literal: true
22

33
class CommentsController < ApplicationController
4-
before_action :set_comment, only: %i[show update destroy]
4+
before_action :set_comment, only: %i[show update destroy report]
55

66
def authorize!
77
authorize(@comment || @comments)
@@ -15,12 +15,6 @@ def index
1515
submission = Submission.find_by(id: file.context_id)
1616
if submission
1717
@comments = Comment.where(file_id: params[:file_id])
18-
@comments.map do |comment|
19-
comment.username = comment.user.displayname
20-
comment.date = comment.created_at.strftime('%d.%m.%Y %k:%M')
21-
comment.updated = (comment.created_at != comment.updated_at)
22-
comment.editable = policy(comment).edit?
23-
end
2418
else
2519
@comments = []
2620
end
@@ -67,6 +61,15 @@ def destroy
6761
head :no_content
6862
end
6963

64+
# POST /comments/1/report.json
65+
def report
66+
authorize!
67+
68+
UserContentReportMailer.with(reported_content: @comment).report_content.deliver_later
69+
70+
head :no_content
71+
end
72+
7073
private
7174

7275
# Use callbacks to share common setup or constraints between actions.

app/controllers/request_for_comments_controller.rb

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -167,9 +167,9 @@ def create
167167
def report
168168
authorize!
169169

170-
ReportMailer.with(reported_content: @request_for_comment).report_content.deliver_later
170+
UserContentReportMailer.with(reported_content: @request_for_comment).report_content.deliver_later
171171

172-
redirect_to @request_for_comment, notice: t('.report.reported'), status: :see_other
172+
redirect_to @request_for_comment, notice: t('.reported'), status: :see_other
173173
end
174174

175175
private

app/javascript/sprocket-asset-import/request-for-comments.js

Lines changed: 26 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -112,9 +112,10 @@ $(document).on('turbo-migration:load', function () {
112112
</div> \
113113
<div class="comment-content">' + commentText + '</div> \
114114
<textarea class="comment-editor">' + commentText + '</textarea> \
115-
<div class="comment-actions' + (comment.editable ? '' : ' d-none') + '"> \
116-
<button class="action-edit btn btn-sm btn-warning">' + I18n.t('shared.edit') + '</button> \
117-
<button class="action-delete btn btn-sm btn-danger">' + I18n.t('shared.destroy') + '</button> \
115+
<div class="comment-actions' + (comment.editable || comment.reportable ? '' : ' d-none') + '"> \
116+
<button class="action-edit btn btn-sm btn-warning' + (comment.editable ? '' : ' d-none') + '">' + I18n.t('shared.edit') + '</button> \
117+
<button class="action-delete btn btn-sm btn-danger' + (comment.editable ? '' : ' d-none') + '">' + I18n.t('shared.destroy') + '</button> \
118+
<button class="action-report btn btn-light btn-sm' + (comment.reportable ? '' : ' d-none') + '">' + I18n.t('shared.report') + '</button> \
118119
</div> \
119120
</div>';
120121
});
@@ -166,6 +167,17 @@ $(document).on('turbo-migration:load', function () {
166167
})
167168
}
168169

170+
function reportComment(commentId, callback) {
171+
const jqxhr = $.ajax({
172+
type: 'POST',
173+
url: Routes.report_comment_path(commentId)
174+
});
175+
jqxhr.done(function () {
176+
callback();
177+
});
178+
jqxhr.fail(ajaxError);
179+
}
180+
169181
function deleteComment(commentId, editor, file_id, callback) {
170182
const jqxhr = $.ajax({
171183
type: 'DELETE',
@@ -313,6 +325,17 @@ $(document).on('turbo-migration:load', function () {
313325
const container = otherComments.find('.container');
314326
container.html(htmlContent);
315327

328+
const reportButtons = container.find('.action-report');
329+
reportButtons.on('click', function (event) {
330+
const button = $(event.target);
331+
const parent = $(button).parent().parent();
332+
const commentId = parent.data('comment-id');
333+
334+
reportComment(commentId, function () {
335+
parent.html('<div class="comment-reported">' + I18n.t('comments.reported') + '</div>');
336+
});
337+
});
338+
316339
const deleteButtons = container.find('.action-delete');
317340
deleteButtons.on('click', function (event) {
318341
const button = $(event.target);

app/mailers/report_mailer.rb

Lines changed: 0 additions & 18 deletions
This file was deleted.
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
# frozen_string_literal: true
2+
3+
class UserContentReportMailer < ApplicationMailer
4+
default to: CodeOcean::Config.new(:code_ocean).read.dig(:content_moderation, :report_emails)
5+
6+
def report_content
7+
@user_content_report = UserContentReport.new(reported_content: params.fetch(:reported_content))
8+
9+
mail(subject: I18n.t('user_content_report_mailer.report_content.subject', human_model_name: @user_content_report.human_model_name))
10+
end
11+
end

app/models/comment.rb

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,6 @@ class Comment < ApplicationRecord
55
include Creation
66
include ActionCableHelper
77

8-
attr_accessor :username, :date, :updated, :editable
9-
108
belongs_to :file, class_name: 'CodeOcean::File'
119
has_one :submission, through: :file, source: :context, source_type: 'Submission'
1210
has_one :request_for_comment, through: :submission

app/policies/comment_policy.rb

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,14 @@
11
# frozen_string_literal: true
22

33
class CommentPolicy < ApplicationPolicy
4+
REPORT_RECEIVER_CONFIGURED = CodeOcean::Config.new(:code_ocean).read.dig(:content_moderation, :report_emails).present?
5+
46
def create?
5-
everyone
7+
show?
68
end
79

810
def show?
9-
everyone
11+
Pundit.policy(@user, @record.request_for_comment).show? && everyone
1012
end
1113

1214
%i[destroy? update? edit?].each do |action|
@@ -16,4 +18,8 @@ def show?
1618
def index?
1719
everyone
1820
end
21+
22+
def report?
23+
REPORT_RECEIVER_CONFIGURED && show? && !author?
24+
end
1925
end
Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,11 @@
11
# frozen_string_literal: true
22

33
json.array!(@comments) do |comment|
4-
json.extract! comment, :id, :user_id, :file_id, :row, :column, :text, :username, :date, :updated, :editable
4+
json.extract! comment, :id, :user_id, :file_id, :row, :column, :text
5+
json.username comment.user.displayname
6+
json.date comment.created_at.strftime('%d.%m.%Y %k:%M')
7+
json.updated(comment.created_at != comment.updated_at)
8+
json.editable policy(comment).edit?
9+
json.reportable policy(comment).report?
510
json.url comment_url(comment, format: :json)
611
end

app/views/report_mailer/report_content.html.slim

Lines changed: 0 additions & 6 deletions
This file was deleted.

0 commit comments

Comments
 (0)