Merge pull request #908 from chrishunt/chrishunt/extract-topic-status-update

Extract topic status update
This commit is contained in:
Robin Ward 2013-05-28 10:00:49 -07:00
commit 8d47f92c27
3 changed files with 69 additions and 23 deletions

View File

@ -193,6 +193,10 @@ class Topic < ActiveRecord::Base
@post_numbers ||= posts.order(:post_number).pluck(:post_number)
end
def age_in_days
((Time.zone.now - created_at) / 1.day).round
end
def has_meta_data_boolean?(key)
meta_data_string(key) == 'true'
end
@ -249,29 +253,8 @@ class Topic < ActiveRecord::Base
.all
end
def update_status(property, status, user)
Topic.transaction do
# Special case: if it's pinned, update that
if property.to_sym == :pinned
update_pinned(status)
else
# otherwise update the column
update_column(property == 'autoclosed' ? 'closed' : property, status)
end
key = "topic_statuses.#{property}_"
key << (status ? 'enabled' : 'disabled')
opts = {}
# We don't bump moderator posts except for the re-open post.
opts[:bump] = true if (property == 'closed' or property == 'autoclosed') and (!status)
message = property != 'autoclosed' ? I18n.t(key) : I18n.t(key, count: (((self.auto_close_at||Time.zone.now) - self.created_at) / 86_400).round )
add_moderator_post(user, message, opts)
end
def update_status(status, enabled, user)
TopicStatusUpdate.new(self, user).update! status, enabled
end
# Atomically creates the next post number

View File

@ -0,0 +1,56 @@
TopicStatusUpdate = Struct.new(:topic, :user) do
def update!(status, enabled)
status = Status.new(status, enabled)
Topic.transaction do
change status
create_moderator_post_for status
end
end
private
def change(status)
if status.pinned?
topic.update_pinned status.enabled?
elsif status.autoclosed?
topic.update_column 'closed', status.enabled?
else
topic.update_column status.name, status.enabled?
end
end
def create_moderator_post_for(status)
topic.add_moderator_post(user, message_for(status), options_for(status))
end
def message_for(status)
I18n.t status.locale_key, count: topic.age_in_days
end
def options_for(status)
{ bump: status.reopening_topic? }
end
Status = Struct.new(:name, :enabled) do
%w(pinned autoclosed closed).each do |status|
define_method("#{status}?") { name == status }
end
def enabled?
enabled
end
def disabled?
!enabled?
end
def locale_key
"topic_statuses.#{name}_#{enabled? ? 'enabled' : 'disabled'}"
end
def reopening_topic?
(closed? || autoclosed?) && disabled?
end
end
end

View File

@ -630,6 +630,13 @@ describe Topic do
context 'autoclosed' do
let(:status) { 'autoclosed' }
it_should_behave_like 'a status that closes a topic'
it 'puts the autoclose duration in the moderator post' do
@topic.created_at = 3.days.ago
@topic.update_status(status, true, @user)
expect(@topic.posts.last.raw).to include "closed after 3 days"
end
end