<commit_before>require "download"

class PostController < ApplicationController
  layout 'default'
  helper :avatar

  verify :method => :post, :only => [:update, :destroy, :create, :revert_tags, :vote, :flag], :redirect_to => {:action => :show, :id => lambda {|c| c.params[:id]}}

  before_filter :member_only, :only => [:create, :destroy, :delete, :flag, :revert_tags, :activate, :update_batch, :vote]
  before_filter :post_member_only, :only => [:update, :upload, :flag]
  before_filter :janitor_only, :only => [:moderate, :undelete]
  after_filter :save_tags_to_cookie, :only => [:update, :create]
  if CONFIG["load_average_threshold"]
    before_filter :check_load_average, :only => [:index, :popular_by_day, :popular_by_week, :popular_by_month, :random, :atom, :piclens]
  end

  around_filter :cache_action, :only => [:index, :atom, :piclens]

  helper :wiki, :tag, :comment, :pool, :favorite, :advertisements

  def verify_action(options)
    redirect_to_proc = false

    if options[:redirect_to] && options[:redirect_to][:id].is_a?(Proc)
      redirect_to_proc = options[:redirect_to][:id]
      options[:redirect_to][:id] = options[:redirect_to][:id].call(self)
    end

    result = super(options)

    if redirect_to_proc
      options[:redirect_to][:id] = redirect_to_proc
    end

    return result
  end

  def activate
    ids = params[:post_ids].map { |id| id.to_i }
    changed = Post.batch_activate(@current_user.is_mod_or_higher? ? nil: @current_user.id, ids)
    respond_to_success("Posts activated", {:action => "moderate"}, :api => {:count => changed})
  end

  def upload_problem
  end

  def upload
    set_title "Upload"

    @deleted_posts = FlaggedPostDetail.new_deleted_posts(@current_user)
#    if params[:url]
#      @post = Post.find(:first, :conditions => ["source = ?", params[:url]])
#    end

    if @post.nil?
      @post = Post.new
    end
  end

  def create
    if @current_user.is_member_or_lower? && Post.count(:conditions => ["user_id = ? AND created_at > ? ", @current_user.id, 1.day.ago]) >= CONFIG["member_post_limit"]
      respond_to_error("Daily limit exceeded", {:action => "error"}, :status => 421)
      return
    end

    if @current_user.is_privileged_or_higher?
      status = "active"
    else
      status = "pending"
    end

    @post = Post.create(params[:post].merge(:updater_user_id => @current_user.id, :updater_ip_addr => request.ip, :user_id => @current_user.id, :ip_addr => request.ip, :status => status))

    if @post.errors.empty?
      if params[:md5] && @post.md5 != params[:md5].downcase
        @post.destroy
        respond_to_error("MD5 mismatch", {:action => "error"}, :status => 420)
      else
        api_data = {:post_id => @post.id, :location => url_for(:controller => "post", :action => "show", :id => @post.id)}
        if CONFIG["dupe_check_on_upload"] && @post.image? && @post.parent_id.nil?
          if params[:format] == "xml" || params[:format] == "json"
            options = { :services => SimilarImages.get_services("local"), :type => :post, :source => @post }

            res = SimilarImages.similar_images(options)
            if not res[:posts].empty?
              @post.tags = @post.tags + " possible_duplicate"
              @post.save!
              api_data[:has_similar_hits] = true
            end
          end

          api_data[:similar_location] = url_for(:controller => "post", :action => "similar", :id => @post.id, :initial => 1)
          respond_to_success("Post uploaded", {:controller => "post", :action => "similar", :id => @post.id, :initial => 1}, :api => api_data)
        else
          respond_to_success("Post uploaded", {:controller => "post", :action => "show", :id => @post.id, :tag_title => @post.tag_title}, :api => api_data)
        end
      end
    elsif @post.errors.invalid?(:md5)
      p = Post.find_by_md5(@post.md5)

      update = { :tags => p.cached_tags + " " + params[:post][:tags], :updater_user_id => session[:user_id], :updater_ip_addr => request.ip }
      update[:source] = @post.source if p.source.blank? && !@post.source.blank?
      p.update_attributes(update)

      api_data = {
        :location => url_for(:controller => "post", :action => "show", :id => p.id),
        :post_id => p.id
      }
      respond_to_error("Post already exists", {:controller => "post", :action => "show", :id => p.id, :tag_title => @post.tag_title}, :api => api_data, :status => 423)
    else
      respond_to_error(@post, :action => "error")
    end
  end

  def moderate
    set_title "Moderation queue"

    if request.post?
      posts = []

      Post.transaction do
        if params[:ids]
          params[:ids].keys.each do |post_id|
            post = Post.find(post_id)
            if params[:commit] == "Approve"
              post.approve!(@current_user.id)
            elsif params[:commit] == "Delete"
              post.destroy_with_reason(params[:reason] || params[:reason2], @current_user)

              # Include post data for the parent: deleted posts aren't counted as children, so
              # their has_children attribute may change.
              posts << post.get_parent if not post.parent_id.nil?
            end
            post.reload
            posts << post
          end
        end
      end
      posts.uniq!

      api_data = Post.batch_api_data(posts) if params[:format] == "json" || params[:format] == "xml"

      if params[:commit] == "Approve"
        respond_to_success("Post approved", {:action => "moderate"}, :api => api_data)
      elsif params[:commit] == "Delete"
        respond_to_success("Post deleted", {:action => "moderate"}, :api => api_data)
      end
    else
      if params[:query]
        @pending_posts = Post.find_by_sql(Post.generate_sql(params[:query], :pending => true, :order => "id desc"))
        @flagged_posts = Post.find_by_sql(Post.generate_sql(params[:query], :flagged => true, :order => "id desc"))
      else
        @pending_posts = Post.find(:all, :conditions => "status = 'pending'", :order => "id desc")
        @flagged_posts = Post.find(:all, :conditions => "status = 'flagged'", :order => "id desc")
      end
    end
  end

  def update
    @post = Post.find(params[:id])
    user_id = @current_user.id

    Post.filter_api_changes(params[:post])

    if @post.update_attributes(params[:post].merge(:updater_user_id => user_id, :updater_ip_addr => request.ip))
      # Reload the post to send the new status back; not all changes will be reflected in
      # @post due to after_save changes.
      @post.reload

      api_data = @post.api_data if params[:format] == "json" || params[:format] == "xml"
      respond_to_success("Post updated", {:action => "show", :id => @post.id, :tag_title => @post.tag_title}, :api => api_data)
    else
      respond_to_error(@post, :action => "show", :id => params[:id])
    end
  end
<commit_msg>Added authorization for updating (deleted) post.<commit_after>require "download"

class PostController < ApplicationController
  layout 'default'
  helper :avatar

  verify :method => :post, :only => [:update, :destroy, :create, :revert_tags, :vote, :flag], :redirect_to => {:action => :show, :id => lambda {|c| c.params[:id]}}

  before_filter :member_only, :only => [:create, :destroy, :delete, :flag, :revert_tags, :activate, :update_batch, :vote]
  before_filter :post_member_only, :only => [:update, :upload, :flag]
  before_filter :janitor_only, :only => [:moderate, :undelete]
  after_filter :save_tags_to_cookie, :only => [:update, :create]
  if CONFIG["load_average_threshold"]
    before_filter :check_load_average, :only => [:index, :popular_by_day, :popular_by_week, :popular_by_month, :random, :atom, :piclens]
  end

  around_filter :cache_action, :only => [:index, :atom, :piclens]

  helper :wiki, :tag, :comment, :pool, :favorite, :advertisements

  def verify_action(options)
    redirect_to_proc = false

    if options[:redirect_to] && options[:redirect_to][:id].is_a?(Proc)
      redirect_to_proc = options[:redirect_to][:id]
      options[:redirect_to][:id] = options[:redirect_to][:id].call(self)
    end

    result = super(options)

    if redirect_to_proc
      options[:redirect_to][:id] = redirect_to_proc
    end

    return result
  end

  def activate
    ids = params[:post_ids].map { |id| id.to_i }
    changed = Post.batch_activate(@current_user.is_mod_or_higher? ? nil: @current_user.id, ids)
    respond_to_success("Posts activated", {:action => "moderate"}, :api => {:count => changed})
  end

  def upload_problem
  end

  def upload
    set_title "Upload"

    @deleted_posts = FlaggedPostDetail.new_deleted_posts(@current_user)
#    if params[:url]
#      @post = Post.find(:first, :conditions => ["source = ?", params[:url]])
#    end

    if @post.nil?
      @post = Post.new
    end
  end

  def create
    if @current_user.is_member_or_lower? && Post.count(:conditions => ["user_id = ? AND created_at > ? ", @current_user.id, 1.day.ago]) >= CONFIG["member_post_limit"]
      respond_to_error("Daily limit exceeded", {:action => "error"}, :status => 421)
      return
    end

    if @current_user.is_privileged_or_higher?
      status = "active"
    else
      status = "pending"
    end

    @post = Post.create(params[:post].merge(:updater_user_id => @current_user.id, :updater_ip_addr => request.ip, :user_id => @current_user.id, :ip_addr => request.ip, :status => status))

    if @post.errors.empty?
      if params[:md5] && @post.md5 != params[:md5].downcase
        @post.destroy
        respond_to_error("MD5 mismatch", {:action => "error"}, :status => 420)
      else
        api_data = {:post_id => @post.id, :location => url_for(:controller => "post", :action => "show", :id => @post.id)}
        if CONFIG["dupe_check_on_upload"] && @post.image? && @post.parent_id.nil?
          if params[:format] == "xml" || params[:format] == "json"
            options = { :services => SimilarImages.get_services("local"), :type => :post, :source => @post }

            res = SimilarImages.similar_images(options)
            if not res[:posts].empty?
              @post.tags = @post.tags + " possible_duplicate"
              @post.save!
              api_data[:has_similar_hits] = true
            end
          end

          api_data[:similar_location] = url_for(:controller => "post", :action => "similar", :id => @post.id, :initial => 1)
          respond_to_success("Post uploaded", {:controller => "post", :action => "similar", :id => @post.id, :initial => 1}, :api => api_data)
        else
          respond_to_success("Post uploaded", {:controller => "post", :action => "show", :id => @post.id, :tag_title => @post.tag_title}, :api => api_data)
        end
      end
    elsif @post.errors.invalid?(:md5)
      p = Post.find_by_md5(@post.md5)

      update = { :tags => p.cached_tags + " " + params[:post][:tags], :updater_user_id => session[:user_id], :updater_ip_addr => request.ip }
      update[:source] = @post.source if p.source.blank? && !@post.source.blank?
      p.update_attributes(update)

      api_data = {
        :location => url_for(:controller => "post", :action => "show", :id => p.id),
        :post_id => p.id
      }
      respond_to_error("Post already exists", {:controller => "post", :action => "show", :id => p.id, :tag_title => @post.tag_title}, :api => api_data, :status => 423)
    else
      respond_to_error(@post, :action => "error")
    end
  end

  def moderate
    set_title "Moderation queue"

    if request.post?
      posts = []

      Post.transaction do
        if params[:ids]
          params[:ids].keys.each do |post_id|
            post = Post.find(post_id)
            if params[:commit] == "Approve"
              post.approve!(@current_user.id)
            elsif params[:commit] == "Delete"
              post.destroy_with_reason(params[:reason] || params[:reason2], @current_user)

              # Include post data for the parent: deleted posts aren't counted as children, so
              # their has_children attribute may change.
              posts << post.get_parent if not post.parent_id.nil?
            end
            post.reload
            posts << post
          end
        end
      end
      posts.uniq!

      api_data = Post.batch_api_data(posts) if params[:format] == "json" || params[:format] == "xml"

      if params[:commit] == "Approve"
        respond_to_success("Post approved", {:action => "moderate"}, :api => api_data)
      elsif params[:commit] == "Delete"
        respond_to_success("Post deleted", {:action => "moderate"}, :api => api_data)
      end
    else
      if params[:query]
        @pending_posts = Post.find_by_sql(Post.generate_sql(params[:query], :pending => true, :order => "id desc"))
        @flagged_posts = Post.find_by_sql(Post.generate_sql(params[:query], :flagged => true, :order => "id desc"))
      else
        @pending_posts = Post.find(:all, :conditions => "status = 'pending'", :order => "id desc")
        @flagged_posts = Post.find(:all, :conditions => "status = 'flagged'", :order => "id desc")
      end
    end
  end

  def update
    @post = Post.find(params[:id])
    if @post.is_deleted? and not @current_user.is_mod_or_higher?
      respond_to_error('Post Locked', { :action => :show, :id => params[:id] }, { :status => 422 })
      return
    end
    user_id = @current_user.id

    Post.filter_api_changes(params[:post])

    if @post.update_attributes(params[:post].merge(:updater_user_id => user_id, :updater_ip_addr => request.ip))
      # Reload the post to send the new status back; not all changes will be reflected in
      # @post due to after_save changes.
      @post.reload

      api_data = @post.api_data if params[:format] == "json" || params[:format] == "xml"
      respond_to_success("Post updated", {:action => "show", :id => @post.id, :tag_title => @post.tag_title}, :api => api_data)
    else
      respond_to_error(@post, :action => "show", :id => params[:id])
    end
  end

{'fraction_non_alphanumeric': 0.15753178650958982, 'fraction_numerical': 0.0030888585590115652, 'mean_word_length': 3.1695118298891884, 'pattern_counts': {'":': 0, '<': 13, '<?xml version=': 0, '>': 174, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 6}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 2, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2995179', 'n_tokens_mistral': 4614, 'n_tokens_neox': 4449, 'n_words': 1020}