Skip to content

Commit

Permalink
feat: user can now report the forum post as spam
Browse files Browse the repository at this point in the history
  • Loading branch information
Waishnav committed Jun 25, 2024
1 parent 3277338 commit fa01c1c
Show file tree
Hide file tree
Showing 13 changed files with 120 additions and 27 deletions.
2 changes: 2 additions & 0 deletions app/assets/javascripts/simple_discussion/controllers/index.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import { application } from "./application"

import DropdownController from "./dropdown_controller"
import ReportSpamController from "./report_spam_controller";

application.register("dropdown", DropdownController);
application.register("report-spam", ReportSpamController);
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import { Controller } from "@hotwired/stimulus"

export default class extends Controller {
static targets = ["reportSpamButton"]

connect() {
const reportSpamForm = document.getElementById("reportSpamForm")
const postId = this.element.dataset.postId
this.reportSpamButtonTarget.addEventListener("click", () => {
const formActionArray = reportSpamForm.action.split("/")
if (formActionArray[formActionArray.length - 2] === "threads") {
reportSpamForm.action += `/posts/${postId}/report_spam`
} else {
reportSpamForm.action = reportSpamForm.action.replace(/\/\d+\//, `/${postId}/`)
}
})
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ def is_moderator_or_owner?(object)
helper_method :is_moderator_or_owner?

def is_moderator?
current_user.moderator?
current_user&.moderator?
end
helper_method :is_moderator?

Expand Down
11 changes: 11 additions & 0 deletions app/controllers/simple_discussion/forum_posts_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,17 @@ def unsolved
redirect_to simple_discussion.forum_thread_path(@forum_thread, anchor: ActionView::RecordIdentifier.dom_id(@forum_post))
end

def report_spam
@forum_post = @forum_thread.forum_posts.find(params[:id])
@spam_report = SpamReport.new(forum_post: @forum_post, user: current_user, reason: params[:reason], details: params[:details])

if @spam_report.save
redirect_to simple_discussion.forum_thread_path(@forum_thread, anchor: ActionView::RecordIdentifier.dom_id(@forum_post))
else
render template: "simple_discussion/forum_threads/show"
end
end

private

def set_forum_thread
Expand Down
1 change: 1 addition & 0 deletions app/models/forum_post.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
class ForumPost < ApplicationRecord
belongs_to :forum_thread, counter_cache: true, touch: true
belongs_to :user
has_many :spam_posts, dependent: :destroy

validate :clean_body
validates :user_id, :body, presence: true
Expand Down
15 changes: 15 additions & 0 deletions app/models/spam_report.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
class SpamReport < ApplicationRecord
belongs_to :forum_post
belongs_to :user

validates :forum_post_id, :user_id, :reason, presence: true
validates :details, presence: true, if: -> { reason == 'other' }

enum reason: {
sexual_content: 0,
violent_content: 1,
irrelevant_content: 2,
misleading_content: 3,
others: 4
}
end
44 changes: 20 additions & 24 deletions app/views/simple_discussion/forum_posts/_forum_post.html.erb
Original file line number Diff line number Diff line change
@@ -1,42 +1,38 @@
<%# We don't currently cache the forum posts because they have permissions to deal with %>

<%= content_tag :div, id: forum_post.solved ? 'solution' : dom_id(forum_post), class: "forum-post" do %>
<div class="forum-post-header">
<% if is_moderator_or_owner?(forum_post) %>
<div class="float-right d-flex align-items-center">
<% if forum_post.solved? %>
<span class="badge badge-success p-2 mr-2"><%= t('solution') %></span>
<% end %>
<div class="float-right d-flex align-items-center">
<% if forum_post.solved? %>
<span class="badge badge-success p-2 mr-2"><%= t('solution') %></span>
<% end %>
<% if user_signed_in? %>
<div class="dropdown" data-controller="dropdown">
<button class="btn btn-light bg-white" role="button" data-dropdown-target="dropdownButton">
<%= icon("fas","ellipsis-v") %>
</button>
<div class="dropdown-menu dropdown-menu-right" data-dropdown-target="dropdownMenu">
<%= link_to t('report_spam'), "#", class: "dropdown-item", data: { controller: "report-spam", report_spam_target: "reportSpamButton", toggle: "modal", target: "#reportSpamModal", post_id: forum_post.id } %>
<% if is_moderator_or_owner?(forum_post) %>
<%= link_to t('edit_post'), simple_discussion.edit_forum_thread_forum_post_path(@forum_thread, forum_post),
class: "dropdown-item",
data: { toggle: "tooltip", placement: "left" },
title: t('edit_this_post') %>
class: "dropdown-item",
data: { toggle: "tooltip", placement: "left" },
title: t('edit_this_post') %>
<%= link_to t('delete_post'), simple_discussion.forum_thread_forum_post_path(@forum_thread, forum_post),
class: "dropdown-item",
method: :delete,
data: { toggle: "tooltip", placement: "left", confirm: "Are you sure you want to delete this post?" },
title: t('delete_this_post') %>
<% end %>
class: "dropdown-item",
method: :delete,
data: { toggle: "tooltip", placement: "left", confirm: "Are you sure you want to delete this post?" },
title: t('delete_this_post') %>
<% end %>
<% if is_moderator_or_owner?(@forum_thread) %>
<% if @forum_thread.solved? && forum_post.solved? %>
<% if is_moderator_or_owner?(@forum_thread) %>
<%= link_to t('unmark_as_solution'), simple_discussion.unsolved_forum_thread_forum_post_path(@forum_thread, forum_post), class: "dropdown-item", method: :put %>
<%= link_to t('unmark_as_solution'), simple_discussion.unsolved_forum_thread_forum_post_path(@forum_thread, forum_post), class: "dropdown-item", method: :put %>
<% else %>
<%= link_to t('mark_as_solution'), simple_discussion.solved_forum_thread_forum_post_path(@forum_thread, forum_post), method: :put, class: "dropdown-item" %>
<% end %>
<% elsif is_moderator_or_owner?(@forum_thread) %>
<%= link_to t('mark_as_solution'), simple_discussion.solved_forum_thread_forum_post_path(@forum_thread, forum_post),
method: :put,
class: "dropdown-item"
%>
<% end %>
</div>
</div>
</div>
<% end %>
<% end %>
</div>
<div class="user-details d-flex flex-row">
<div class="user-avatar mr-2" ><img src="<%= gravatar_url_for(forum_post.user.email, size: 30) %>" alt="avatar of user" ></div>
<div class="details d-flex flex-column justify-content-between">
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
<div class="modal fade" id="reportSpamModal" tabindex="-1" role="dialog" aria-labelledby="reportSpamModalLabel" aria-hidden="true">
<div class="modal-dialog modal-dialog-centered" role="document">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="reportSpamModalLabel">Report Post as Spam</h5>
<button type="button" class="close" data-dismiss="modal" aria-label="Close">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
<%= form_with id:"reportSpamForm", url: simple_discussion.forum_thread_path(forum_thread), method: :post, local: true do |f| %>
<% if @spam_report && @spam_report.errors.any? %>
<div class="alert alert-danger" role="alert">
<% @spam_report.errors.full_messages.each do |message| %>
<li><%= message %></li>
<% end %>
</div>
<% end %>

<div class="form-group">
<%= f.collection_radio_buttons :reason, SpamReport.reasons.keys, :to_s, :humanize, include_hidden: false do |b| %>
<div class="form-check">
<%= b.radio_button(class: "form-check-input") %>
<%= b.label(class: "form-check-label") %>
</div>
<% end %>
</div>
<div class="form-group">
<%= f.label :details, "Reason in detail (if others)" %>
<%= f.text_area :details, class: "form-control", rows: 2 %>
</div>
<%= f.submit "Report", class: "btn btn-danger" %>
<% end %>
</div>
</div>
</div>
</div>
1 change: 0 additions & 1 deletion app/views/simple_discussion/forum_threads/_form.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -36,5 +36,4 @@
<%= f.button "Update Thread", class: "btn forum-primary-btn", data: {disable_with: "<i class='fa fa-spinner fa-spin'></i> #{t('saving')}"} %>
<% end %>
</div>

<% end %>
1 change: 1 addition & 0 deletions app/views/simple_discussion/forum_threads/show.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -39,5 +39,6 @@

<%= render partial: "simple_discussion/forum_posts/forum_post", collection: @forum_thread.forum_posts.includes(:user).sorted %>
<%= render partial: "simple_discussion/forum_posts/form" if user_signed_in? %>
<%= render partial: "simple_discussion/forum_posts/report_spam_modal_form", locals: { forum_thread: @forum_thread } if user_signed_in? %>

<%= render partial: "login_bar" if !user_signed_in? %>
2 changes: 1 addition & 1 deletion bin/rails
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
# installed from the root of your application.

ENGINE_ROOT = File.expand_path('..', __dir__)
ENGINE_PATH = File.expand_path('../lib/pay/engine', __dir__)
ENGINE_PATH = File.expand_path('../lib/simple_discussion/engine', __dir__)
APP_PATH = File.expand_path('../test/dummy/config/application', __dir__)

# Set up gems listed in the Gemfile.
Expand Down
1 change: 1 addition & 0 deletions config/routes.rb
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
member do
put :solved
put :unsolved
post :report_spam
end
end

Expand Down
12 changes: 12 additions & 0 deletions db/migrate/20240624124709_create_spam_reports.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
class CreateSpamReports < ActiveRecord::Migration[7.0]
def change
create_table :spam_reports do |t|
t.references :forum_post, null: false, foreign_key: true
t.references :user, null: false, foreign_key: true # The user who reported the post
t.integer :reason, null: false # Enum for reason
t.text :details # optional column if the reason is 'other'

t.timestamps
end
end
end

0 comments on commit fa01c1c

Please sign in to comment.