Skip to content

Commit

Permalink
AO3-4718 Fix permission checks for comments on tags. (otwcode#2883)
Browse files Browse the repository at this point in the history
* AO3-4718 Fix permission checks for tag comments.

* AO3-4718 Better cancel_comment_edit checks.

* AO3-4718 RSpec tests for permission checks.

* AO3-4718 Test for replying to a comment on a tag.
  • Loading branch information
tickinginstant authored and sarken committed Apr 28, 2017
1 parent 96e9aca commit 6e196e0
Show file tree
Hide file tree
Showing 4 changed files with 256 additions and 17 deletions.
13 changes: 5 additions & 8 deletions app/controllers/comments_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,15 @@ class CommentsController < ApplicationController
before_filter :load_commentable, :only => [ :index, :new, :create, :edit, :update,
:show_comments, :hide_comments, :add_comment,
:cancel_comment, :add_comment_reply,
:cancel_comment_reply, :cancel_comment_edit,
:cancel_comment_reply,
:delete_comment, :cancel_comment_delete, :unreviewed, :review_all ]
before_filter :check_user_status, :only => [:new, :create, :edit, :update, :destroy]
before_filter :load_comment, only: [:show, :edit, :update, :delete_comment, :destroy, :approve, :reject]
before_filter :load_comment, only: [:show, :edit, :update, :delete_comment, :destroy, :cancel_comment_edit, :cancel_comment_delete, :review, :approve, :reject]
before_filter :check_visibility, :only => [:show]
before_filter :check_if_restricted
before_filter :check_tag_wrangler_access, :only => [:index, :show]
before_filter :check_tag_wrangler_access
before_filter :check_pseud_ownership, :only => [:create, :update]
before_filter :check_ownership, :only => [:edit, :update]
before_filter :check_ownership, only: [:edit, :update, :cancel_comment_edit]
before_filter :check_permission_to_edit, :only => [:edit, :update ]
before_filter :check_permission_to_delete, :only => [:delete_comment, :destroy]
before_filter :check_anonymous_comment_preference, :only => [:new, :create, :add_comment_reply]
Expand Down Expand Up @@ -111,7 +111,7 @@ def check_permission_to_moderate
end

def check_tag_wrangler_access
if @commentable.is_a?(Tag) || (@comment && @comment.commentable.is_a?(Tag))
if @commentable.is_a?(Tag) || (@comment && @comment.parent.is_a?(Tag))
logged_in_as_admin? || permit?("tag_wrangler") || access_denied
end
end
Expand Down Expand Up @@ -323,7 +323,6 @@ def destroy
end

def review
@comment = Comment.find(params[:id])
if @comment && current_user_owns?(@comment.ultimate_parent) && @comment.unreviewed?
@comment.toggle!(:unreviewed)
# mark associated inbox comments as read
Expand Down Expand Up @@ -453,7 +452,6 @@ def cancel_comment_reply
end

def cancel_comment_edit
@comment = Comment.find(params[:id])
respond_to do |format|
format.html { redirect_to_comment(@comment) }
format.js
Expand All @@ -473,7 +471,6 @@ def delete_comment
end

def cancel_comment_delete
@comment = Comment.find(params[:id])
respond_to do |format|
format.html do
options = {}
Expand Down
4 changes: 4 additions & 0 deletions features/step_definitions/comment_steps.rb
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,10 @@
step %{I follow "Yes, delete!"}
end

When /^I view the latest comment$/ do
visit comment_path(Comment.last)
end

Given(/^the moderated work "([^\"]*?)" by "([^\"]*?)"$/) do |work, user|
step %{I am logged in as "#{user}"}
step %{I set up the draft "#{work}"}
Expand Down
23 changes: 23 additions & 0 deletions features/tags_and_wrangling/tag_comment.feature
Original file line number Diff line number Diff line change
Expand Up @@ -242,3 +242,26 @@ I'd like to comment on a tag'
# all it checks is that the pagination links aren't broken
When I follow "Next" within ".pagination"
Then I should see "And now things should not break!"

Scenario: Comments on a tag should not be visible to non-wranglers.

Given a canonical fandom "World Domination"
And I am logged in as a tag wrangler
And I post the comment "Top-secret plans." on the tag "World Domination"
And I am logged out

When I view the latest comment

Then I should not see "Top-secret plans."

Scenario: Comments replying to a comment on a tag should not be visible to non-wranglers.

Given a canonical fandom "World Domination"
And I am logged in as a tag wrangler
And I post the comment "Anyone have a plan?" on the tag "World Domination"
And I reply to a comment with "Top-secret plans."
And I am logged out

When I view the latest comment

Then I should not see "Top-secret plans."
233 changes: 224 additions & 9 deletions spec/controllers/comments_controller_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -82,11 +82,55 @@
expect(assigns(:name)).to eq(admin_post.title)
end

it "renders the :new template if commentable is a valid tag" do
fandom = create(:fandom)
post :new, tag_id: fandom.name
expect(response).to render_template("new")
expect(assigns(:name)).to eq("Fandom")
context "when the commentable is a valid tag" do
let(:fandom) { create(:fandom) }

context "when logged in as an admin" do
before { fake_login_admin(create(:admin)) }

it "renders the :new template" do
post :new, tag_id: fandom.name
expect(response).to render_template("new")
expect(assigns(:name)).to eq("Fandom")
end
end

context "when logged in as a tag wrangler" do
before do
fake_login
@current_user.roles << Role.new(name: 'tag_wrangler')
end

it "renders the :new template" do
post :new, tag_id: fandom.name
expect(response).to render_template("new")
expect(assigns(:name)).to eq("Fandom")
end
end

context "when logged in as a random user" do
before { fake_login }

it "shows an error and redirects" do
post :new, tag_id: fandom.name
it_redirects_to_with_error(user_path(@current_user),
"Sorry, you don't have permission to " \
"access the page you were trying to " \
"reach.")
end
end

context "when logged out" do
before { fake_logout }

it "shows an error and redirects" do
post :new, tag_id: fandom.name
it_redirects_to_with_error(new_user_session_path,
"Sorry, you don't have permission to " \
"access the page you were trying to " \
"reach. Please log in.")
end
end
end

it "renders the :new template if commentable is a valid comment" do
Expand All @@ -97,6 +141,75 @@
end
end

describe "POST #create" do
let(:anon_comment_attributes) do
attributes_for(:comment).slice(:name, :email, :content)
end

context "when the commentable is a valid tag" do
let(:fandom) { create(:fandom) }

context "when logged in as an admin" do
before { fake_login_admin(create(:admin)) }

it "posts the comment and shows it in context" do
post :create, tag_id: fandom.name, comment: anon_comment_attributes
comment = Comment.last
expect(comment.commentable).to eq fandom
expect(comment.name).to eq anon_comment_attributes[:name]
expect(comment.email).to eq anon_comment_attributes[:email]
expect(comment.content).to include anon_comment_attributes[:content]
path = comments_path(tag_id: fandom.to_param,
anchor: "comment_#{comment.id}")
expect(response).to redirect_to path
end
end

context "when logged in as a tag wrangler" do
before do
fake_login
@current_user.roles << Role.new(name: 'tag_wrangler')
end

it "posts the comment and shows it in context" do
post :create, tag_id: fandom.name, comment: anon_comment_attributes
comment = Comment.last
expect(comment.commentable).to eq fandom
expect(comment.name).to eq anon_comment_attributes[:name]
expect(comment.email).to eq anon_comment_attributes[:email]
expect(comment.content).to include anon_comment_attributes[:content]
path = comments_path(tag_id: fandom.to_param,
anchor: "comment_#{comment.id}")
expect(response).to redirect_to path
end
end

context "when logged in as a random user" do
before { fake_login }

it "shows an error and redirects" do
post :create, tag_id: fandom.name, comment: anon_comment_attributes
it_redirects_to_with_error(user_path(@current_user),
"Sorry, you don't have permission to " \
"access the page you were trying to " \
"reach.")
end
end

context "when logged out" do
before { fake_logout }

it "shows an error and redirects" do
post :create, tag_id: fandom.name, comment: anon_comment_attributes
it_redirects_to_with_error(new_user_session_path,
"Sorry, you don't have permission to " \
"access the page you were trying to " \
"reach. Please log in.")
end
end
end
end

describe "PUT #review_all" do
xit "redirects to root path with an error if current user does not own the commentable" do
fake_login
Expand Down Expand Up @@ -241,6 +354,71 @@
end
end

describe "GET #show_comments" do
context "when the commentable is a valid tag" do
let(:fandom) { create(:fandom) }

let(:all_comments_path) do
comments_path(tag_id: fandom.to_param, anchor: "comments")
end

context "when logged in as an admin" do
before { fake_login_admin(create(:admin)) }

it "redirects to the tag comments page when the format is html" do
get :show_comments, tag_id: fandom.name
expect(response).to redirect_to all_comments_path
end

it "loads the comments when the format is javascript" do
get :show_comments, tag_id: fandom.name, format: :js
expect(response).to render_template(:show_comments)
end
end

context "when logged in as a tag wrangler" do
before do
fake_login
@current_user.roles << Role.new(name: 'tag_wrangler')
end

it "redirects to the tag comments page when the format is html" do
get :show_comments, tag_id: fandom.name
expect(response).to redirect_to all_comments_path
end

it "loads the comments when the format is javascript" do
get :show_comments, tag_id: fandom.name, format: :js
expect(response).to render_template(:show_comments)
end
end

context "when logged in as a random user" do
before { fake_login }

it "shows an error and redirects" do
get :show_comments, tag_id: fandom.name
it_redirects_to_with_error(user_path(@current_user),
"Sorry, you don't have permission to " \
"access the page you were trying to " \
"reach.")
end
end

context "when logged out" do
before { fake_logout }

it "shows an error and redirects" do
get :show_comments, tag_id: fandom.name
it_redirects_to_with_error(new_user_session_path,
"Sorry, you don't have permission to " \
"access the page you were trying to " \
"reach. Please log in.")
end
end
end
end

describe "GET #hide_comments" do
it "redirects to the comment path without an error" do
get :hide_comments, comment_id: unreviewed_comment.id
Expand Down Expand Up @@ -304,10 +482,47 @@
end

describe "GET #cancel_comment_edit" do
it "redirects to the comment on the commentable without an error" do
get :cancel_comment_edit, id: comment.id
expect(flash[:error]).to be_nil
expect(response).to redirect_to(work_path(comment.ultimate_parent, show_comments: true, anchor: "comment_#{comment.id}"))
context "when logged in as the comment writer" do
before { fake_login_known_user(comment.pseud.user) }

context "when the format is html" do
it "redirects to the comment on the commentable without an error" do
get :cancel_comment_edit, id: comment.id
expect(flash[:error]).to be_nil
expect(response).to redirect_to(work_path(comment.ultimate_parent, show_comments: true, anchor: "comment_#{comment.id}"))
end
end

context "when the format is javascript" do
it "loads the javascript to restore the comment" do
get :cancel_comment_edit, id: comment.id, format: :js
expect(response).to render_template("cancel_comment_edit")
end
end
end

context "when logged in as a random user" do
before { fake_login }

it "shows an error and redirects" do
get :cancel_comment_edit, id: comment.id
it_redirects_to_with_error(comment,
"Sorry, you don't have permission to " \
"access the page you were trying to " \
"reach.")
end
end

context "when logged out" do
before { fake_logout }

it "shows an error and redirects" do
get :cancel_comment_edit, id: comment.id
it_redirects_to_with_error(comment,
"Sorry, you don't have permission to " \
"access the page you were trying to " \
"reach. Please log in.")
end
end
end

Expand Down

0 comments on commit 6e196e0

Please sign in to comment.