From 5b5b5a5931469945b6ab9d3f38b11bad83e4cf72 Mon Sep 17 00:00:00 2001 From: Blake Erickson Date: Tue, 7 May 2019 11:34:15 -0600 Subject: [PATCH] FIX: return an error if a user tries to whisper This commit fixes a bug where a user creates a whisper post via the api but is posted as a regular message because they don't have access to whisper. Now a 403 unauthorized will be returned instead of the whisper param just being ignored for regular users. Staff users should not be affected by this change. https://meta.discourse.org/t/a-whisper-is-posted-as-a-message-if-the-user-is-not-staff-moderator-admin-when-using-the-api/116601 --- app/controllers/posts_controller.rb | 4 +++- config/locales/server.en.yml | 1 + lib/guardian/topic_guardian.rb | 4 ++++ spec/requests/posts_controller_spec.rb | 17 +++++++++++++++++ 4 files changed, 25 insertions(+), 1 deletion(-) diff --git a/app/controllers/posts_controller.rb b/app/controllers/posts_controller.rb index 739580e682c..45e4abab311 100644 --- a/app/controllers/posts_controller.rb +++ b/app/controllers/posts_controller.rb @@ -730,7 +730,9 @@ class PostsController < ApplicationController result[:shared_draft] = true end - if current_user.staff? && SiteSetting.enable_whispers? && params[:whisper] == "true" + if params[:whisper] == "true" + raise Discourse::InvalidAccess.new("invalid_whisper_access", nil, custom_message: "invalid_whisper_access") unless guardian.can_create_whisper? + result[:post_type] = Post.types[:whisper] end diff --git a/config/locales/server.en.yml b/config/locales/server.en.yml index ec82060bd9a..2ca784e5646 100644 --- a/config/locales/server.en.yml +++ b/config/locales/server.en.yml @@ -243,6 +243,7 @@ en: read_only_mode_enabled: "The site is in read only mode. Interactions are disabled." invalid_grant_badge_reason_link: "External or invalid discourse link is not allowed in badge reason" email_template_cant_be_modified: "This email template can't be modified" + invalid_whisper_access: "Either whispers are not enabled or you do not have access to create whisper posts" reading_time: "Reading time" likes: "Likes" diff --git a/lib/guardian/topic_guardian.rb b/lib/guardian/topic_guardian.rb index d6ed4159095..cd78f2eff36 100644 --- a/lib/guardian/topic_guardian.rb +++ b/lib/guardian/topic_guardian.rb @@ -24,6 +24,10 @@ module TopicGuardian is_staff? && SiteSetting.shared_drafts_enabled? end + def can_create_whisper? + is_staff? && SiteSetting.enable_whispers? + end + def can_publish_topic?(topic, category) is_staff? && can_see?(topic) && can_create_topic?(category) end diff --git a/spec/requests/posts_controller_spec.rb b/spec/requests/posts_controller_spec.rb index b5dfb78f9e1..3a095417454 100644 --- a/spec/requests/posts_controller_spec.rb +++ b/spec/requests/posts_controller_spec.rb @@ -696,6 +696,7 @@ describe PostsController do before do SiteSetting.min_first_post_typing_time = 0 + SiteSetting.enable_whispers = true end fab!(:user) { Fabricate(:user) } @@ -774,6 +775,22 @@ describe PostsController do expect(response.status).to eq(200) expect(post_1.topic.user.notifications.count).to eq(1) end + + it 'prevents whispers for regular users' do + post_1 = Fabricate(:post) + user = Fabricate(:user) + user_key = ApiKey.create!(user: user, key: SecureRandom.hex).key + + post "/posts.json", params: { + api_username: user.username, + api_key: user_key, + raw: 'this is test whisper', + topic_id: post_1.topic.id, + reply_to_post_number: 1, + whisper: true + } + expect(response.status).to eq(403) + end end describe "when logged in" do