2022-01-23 10:25:56 -08:00
|
|
|
# frozen_string_literal: true
|
|
|
|
|
|
|
|
module UseCase
|
|
|
|
module Question
|
|
|
|
class Create < UseCase::Base
|
|
|
|
option :source_user_id, type: Types::Coercible::Integer | Types::Nil, optional: true
|
|
|
|
option :target_user_id, type: Types::Coercible::Integer
|
|
|
|
option :content, type: Types::Coercible::String
|
|
|
|
option :anonymous, type: Types::Params::Bool, default: proc { false }
|
|
|
|
option :author_identifier, type: Types::Coercible::String | Types::Nil
|
2022-07-24 13:24:48 -07:00
|
|
|
option :direct, type: Types::Params::Bool, default: proc { true }
|
2022-01-23 10:25:56 -08:00
|
|
|
|
|
|
|
def call
|
2022-11-13 05:26:49 -08:00
|
|
|
check_user
|
2022-11-06 06:01:01 -08:00
|
|
|
check_lock
|
2022-01-23 10:25:56 -08:00
|
|
|
check_anonymous_rules
|
|
|
|
check_blocks
|
|
|
|
|
|
|
|
question = ::Question.create!(
|
|
|
|
content: content,
|
|
|
|
author_is_anonymous: anonymous,
|
|
|
|
author_identifier: author_identifier,
|
2022-07-24 12:56:03 -07:00
|
|
|
user: source_user_id.nil? ? nil : source_user,
|
2022-07-24 13:24:48 -07:00
|
|
|
direct: direct
|
2022-01-23 10:25:56 -08:00
|
|
|
)
|
|
|
|
|
|
|
|
return if filtered?(question)
|
|
|
|
|
2022-07-08 11:40:32 -07:00
|
|
|
increment_asked_count
|
|
|
|
|
2022-01-23 10:25:56 -08:00
|
|
|
inbox = ::Inbox.create!(user: target_user, question: question, new: true)
|
|
|
|
|
|
|
|
{
|
2022-07-23 06:33:28 -07:00
|
|
|
status: 201,
|
|
|
|
resource: question,
|
|
|
|
extra: {
|
|
|
|
inbox:
|
|
|
|
}
|
2022-01-23 10:25:56 -08:00
|
|
|
}
|
|
|
|
end
|
|
|
|
|
|
|
|
private
|
|
|
|
|
2022-11-06 06:01:01 -08:00
|
|
|
def check_lock
|
|
|
|
raise Errors::InboxLocked if target_user.inbox_locked?
|
|
|
|
end
|
|
|
|
|
2022-01-23 10:25:56 -08:00
|
|
|
def check_anonymous_rules
|
|
|
|
if !source_user_id && !anonymous
|
|
|
|
# We can not create a non-anonymous question without a source user
|
|
|
|
raise Errors::BadRequest.new("anonymous must be set to true")
|
|
|
|
end
|
|
|
|
|
2022-01-24 11:48:36 -08:00
|
|
|
# The target user does not want questions from strangers
|
|
|
|
raise Errors::Forbidden.new("no anonymous questions allowed") if !target_user.privacy_allow_anonymous_questions && anonymous
|
2022-01-23 10:25:56 -08:00
|
|
|
end
|
|
|
|
|
|
|
|
def check_blocks
|
2022-01-24 13:46:11 -08:00
|
|
|
return if source_user_id.blank?
|
|
|
|
|
|
|
|
raise Errors::AskingOtherBlockedSelf if target_user.blocking?(source_user)
|
|
|
|
raise Errors::AskingSelfBlockedOther if source_user.blocking?(target_user)
|
2022-01-23 10:25:56 -08:00
|
|
|
end
|
|
|
|
|
2022-11-13 05:26:49 -08:00
|
|
|
def check_user
|
2022-11-13 05:38:11 -08:00
|
|
|
raise Errors::NotAuthorized if target_user.privacy_require_user && !source_user_id
|
2022-11-13 05:26:49 -08:00
|
|
|
end
|
|
|
|
|
2022-01-23 10:25:56 -08:00
|
|
|
def increment_asked_count
|
2022-07-24 13:24:48 -07:00
|
|
|
unless source_user_id && !anonymous && !direct
|
2022-01-23 10:25:56 -08:00
|
|
|
# Only increment the asked count of the source user if the question
|
2022-07-24 13:45:04 -07:00
|
|
|
# is not anonymous, and is not direct, and we actually have a source user
|
2022-01-23 10:25:56 -08:00
|
|
|
return
|
|
|
|
end
|
|
|
|
|
2022-01-24 11:48:36 -08:00
|
|
|
source_user.increment(:asked_count)
|
2022-07-08 11:40:32 -07:00
|
|
|
source_user.save
|
2022-01-23 10:25:56 -08:00
|
|
|
end
|
|
|
|
|
|
|
|
def filtered?(question)
|
|
|
|
target_user.mute_rules.any? { |rule| rule.applies_to? question } ||
|
2022-12-26 17:29:29 -08:00
|
|
|
(anonymous && AnonymousBlock.where(identifier: question.author_identifier, user_id: [target_user.id, nil]).any?) ||
|
2022-12-27 18:04:46 -08:00
|
|
|
(source_user_id && anonymous && AnonymousBlock.where(target_user_id: [source_user.id, nil], user_id: [target_user.id, nil]).any?) ||
|
|
|
|
(source_user_id && target_user.muting?(source_user))
|
2022-01-23 10:25:56 -08:00
|
|
|
end
|
|
|
|
|
|
|
|
def source_user
|
|
|
|
@source_user ||= ::User.find(source_user_id)
|
|
|
|
end
|
|
|
|
|
|
|
|
def target_user
|
|
|
|
@target_user ||= ::User.find(target_user_id)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|