2013-02-09 10:33:07 -05:00
require 'edit_rate_limiter'
2013-12-12 03:41:34 +01:00
2013-02-09 10:33:07 -05:00
class PostRevisor
2013-02-21 18:09:56 -05:00
attr_reader :category_changed
2013-02-09 10:33:07 -05:00
def initialize ( post )
@post = post
end
2014-03-27 22:45:51 -07:00
# Recognized options:
# :edit_reason User-supplied edit reason
2014-03-27 18:28:14 -07:00
# :new_user New owner of the post
2014-03-27 22:45:51 -07:00
# :revised_at changes the date of the revision
# :force_new_version bypass ninja-edit window
# :bypass_bump do not bump the topic, even if last post
# :skip_validation ask ActiveRecord to skip validations
#
def revise! ( editor , new_raw , opts = { } )
@editor , @new_raw , @opts = editor , new_raw , opts
return false unless should_revise?
@post . acting_user = @editor
2013-02-09 10:33:07 -05:00
revise_post
2013-02-21 18:09:56 -05:00
update_category_description
2014-03-18 13:40:40 -04:00
update_topic_excerpt
2013-02-09 10:33:07 -05:00
post_process_post
2013-12-10 13:47:07 -05:00
update_topic_word_counts
2013-03-18 15:12:31 -04:00
@post . advance_draft_sequence
2014-03-18 13:12:07 +11:00
PostAlerter . new . after_save_post ( @post )
2014-03-24 12:19:08 +11:00
publish_revision
2013-12-12 03:41:34 +01:00
2013-02-09 10:33:07 -05:00
true
end
private
2014-03-24 12:19:08 +11:00
def publish_revision
MessageBus . publish ( " /topic/ #{ @post . topic_id } " , {
id : @post . id ,
post_number : @post . post_number ,
updated_at : @post . updated_at ,
type : " revised "
} ,
group_ids : @post . topic . secure_group_ids
)
end
2013-02-09 10:33:07 -05:00
def should_revise?
2014-03-27 18:28:14 -07:00
@post . raw != @new_raw || @opts [ :changed_owner ]
2013-02-09 10:33:07 -05:00
end
def revise_post
if should_create_new_version?
revise_and_create_new_version
else
2013-12-12 03:41:34 +01:00
update_post
2013-02-09 10:33:07 -05:00
end
end
def get_revised_at
@opts [ :revised_at ] || Time . now
end
def should_create_new_version?
2014-03-27 22:45:51 -07:00
@post . last_editor_id != @editor . id ||
2013-11-22 01:52:26 +01:00
get_revised_at - @post . last_version_at > SiteSetting . ninja_edit_window . to_i ||
2014-03-27 18:28:14 -07:00
@opts [ :changed_owner ] == true ||
2013-11-22 01:52:26 +01:00
@opts [ :force_new_version ] == true
2013-02-09 10:33:07 -05:00
end
def revise_and_create_new_version
Post . transaction do
2013-12-12 03:41:34 +01:00
@post . version += 1
2013-02-09 10:33:07 -05:00
@post . last_version_at = get_revised_at
update_post
2014-03-27 22:45:51 -07:00
EditRateLimiter . new ( @editor ) . performed! unless @opts [ :bypass_rate_limiter ] == true
2013-02-09 10:33:07 -05:00
bump_topic unless @opts [ :bypass_bump ]
end
end
def bump_topic
unless Post . where ( 'post_number > ? and topic_id = ?' , @post . post_number , @post . topic_id ) . exists?
@post . topic . update_column ( :bumped_at , Time . now )
end
end
2013-12-10 13:47:07 -05:00
def update_topic_word_counts
Topic . exec_sql ( " UPDATE topics SET word_count = (SELECT SUM(COALESCE(posts.word_count, 0))
FROM posts WHERE posts . topic_id = :topic_id )
WHERE topics . id = :topic_id " , topic_id: @post.topic_id)
end
2013-02-09 10:33:07 -05:00
def update_post
@post . raw = @new_raw
2013-12-10 13:47:07 -05:00
@post . word_count = @new_raw . scan ( / \ w+ / ) . size
2014-03-27 22:45:51 -07:00
@post . last_editor_id = @editor . id
2013-11-15 23:28:16 +01:00
@post . edit_reason = @opts [ :edit_reason ] if @opts [ :edit_reason ]
2014-03-27 18:28:14 -07:00
@post . user_id = @opts [ :new_user ] . id if @opts [ :new_user ]
2013-02-09 10:33:07 -05:00
2014-03-27 22:45:51 -07:00
if @editor == @post . user && @post . hidden && @post . hidden_reason_id == Post . hidden_reasons [ :flag_threshold_reached ]
2013-02-09 10:33:07 -05:00
@post . hidden = false
@post . hidden_reason_id = nil
@post . topic . update_attributes ( visible : true )
PostAction . clear_flags! ( @post , - 1 )
end
2013-03-18 15:54:08 -04:00
@post . extract_quoted_post_numbers
2013-12-31 14:37:43 -05:00
@post . save ( validate : ! @opts [ :skip_validations ] )
2013-03-18 15:54:08 -04:00
@post . save_reply_relationships
2013-02-09 10:33:07 -05:00
end
2013-02-21 18:09:56 -05:00
def update_category_description
# If we're revising the first post, we might have to update the category description
return unless @post . post_number == 1
# Is there a category with our topic id?
2014-05-06 14:41:59 +01:00
category = Category . find_by ( topic_id : @post . topic_id )
2013-02-21 18:09:56 -05:00
return unless category . present?
# If found, update its description
body = @post . cooked
matches = body . scan ( / \ <p \ >(.*) \ < \/ p \ > / )
2013-03-05 01:42:44 +01:00
if matches && matches [ 0 ] && matches [ 0 ] [ 0 ]
2013-02-21 18:09:56 -05:00
new_description = matches [ 0 ] [ 0 ]
new_description = nil if new_description == I18n . t ( " category.replace_paragraph " )
category . update_column ( :description , new_description )
@category_changed = category
end
end
2014-03-18 13:40:40 -04:00
def update_topic_excerpt
@post . topic . update_column ( :excerpt , @post . excerpt ( 220 , strip_links : true ) ) if @post . post_number == 1
end
2013-02-09 10:33:07 -05:00
def post_process_post
@post . invalidate_oneboxes = true
@post . trigger_post_process
end
end