<commit_before>require 'open_food_network/permissions'

module Api
  class ProductsController < Api::BaseController
    respond_to :json

    skip_authorization_check only: [:show, :bulk_products, :overridable]

    def show
      @product = find_product(params[:id])
      render json: @product, serializer: Api::Admin::ProductSerializer
    end

    def create
      authorize! :create, Spree::Product
      params[:product][:available_on] ||= Time.zone.now
      @product = Spree::Product.new(params[:product])
      begin
        if @product.save
          render json: @product, serializer: Api::Admin::ProductSerializer, status: 201
        else
          invalid_resource!(@product)
        end
      rescue ActiveRecord::RecordNotUnique
        @product.permalink = nil
        retry
      end
    end

    def update
      authorize! :update, Spree::Product
      @product = find_product(params[:id])
      if @product.update_attributes(params[:product])
        render json: @product, serializer: Api::Admin::ProductSerializer, status: 200
      else
        invalid_resource!(@product)
      end
    end

    def destroy
      authorize! :delete, Spree::Product
      @product = find_product(params[:id])
      @product.update_attribute(:deleted_at, Time.zone.now)
      @product.variants_including_master.update_all(deleted_at: Time.zone.now)
      render json: @product, serializer: Api::Admin::ProductSerializer, status: 204
    end

    # TODO: This should be named 'managed'. Is the action above used? Maybe we should remove it.
    def bulk_products
      @products = OpenFoodNetwork::Permissions.new(current_api_user).editable_products.
        merge(product_scope).
        order('created_at DESC').
        ransack(params[:q]).result.
        page(params[:page]).per(params[:per_page])

      render_paged_products @products
    end

    def overridable
      producers = OpenFoodNetwork::Permissions.new(current_api_user).
        variant_override_producers.by_name

      @products = paged_products_for_producers producers

      render_paged_products @products
    end

    def soft_delete
      authorize! :delete, Spree::Product
      @product = find_product(params[:product_id])
      authorize! :delete, @product
      @product.destroy
      render json: @product, serializer: Api::Admin::ProductSerializer, status: 204
    end

    # POST /api/products/:product_id/clone
    #
    def clone
      authorize! :create, Spree::Product
      original_product = find_product(params[:product_id])
      authorize! :update, original_product

      @product = original_product.duplicate

      render json: @product, serializer: Api::Admin::ProductSerializer, status: 201
    end

    private

    # Copied and modified from SpreeApi::BaseController to allow
    # enterprise users to access inactive products
    def product_scope
      # This line modified
      if current_api_user.has_spree_role?("admin") || current_api_user.enterprises.present?
        scope = Spree::Product
        if params[:show_deleted]
          scope = scope.with_deleted
        end
      else
        scope = Spree::Product.active
      end

      scope.includes(:master)
    end

    def import_date_scope
      return if params[:import_date].blank?
      Spree::Variant.where(import_date: params[:import_date])
    end

    def paged_products_for_producers(producers)
      Spree::Product.scoped.
        merge(product_scope).
        where(supplier_id: producers).
        by_producer.by_name.
        ransack(params[:q]).result.
        page(params[:page]).per(params[:per_page])
    end

    def render_paged_products(products)
      serializer = ActiveModel::ArraySerializer.new(
        products,
        each_serializer: Api::Admin::ProductSerializer
      )

      render text: {
        products: serializer,
        pagination: pagination_data(products)
      }.to_json
    end

    def pagination_data(results)
      {
        results: results.total_count,
        pages: results.num_pages,
        page: params[:page].to_i,
        per_page: params[:per_page].to_i
      }
    end
  end
end
<commit_msg>Make import_date query modification conditional<commit_after>require 'open_food_network/permissions'

module Api
  class ProductsController < Api::BaseController
    respond_to :json

    skip_authorization_check only: [:show, :bulk_products, :overridable]

    def show
      @product = find_product(params[:id])
      render json: @product, serializer: Api::Admin::ProductSerializer
    end

    def create
      authorize! :create, Spree::Product
      params[:product][:available_on] ||= Time.zone.now
      @product = Spree::Product.new(params[:product])
      begin
        if @product.save
          render json: @product, serializer: Api::Admin::ProductSerializer, status: 201
        else
          invalid_resource!(@product)
        end
      rescue ActiveRecord::RecordNotUnique
        @product.permalink = nil
        retry
      end
    end

    def update
      authorize! :update, Spree::Product
      @product = find_product(params[:id])
      if @product.update_attributes(params[:product])
        render json: @product, serializer: Api::Admin::ProductSerializer, status: 200
      else
        invalid_resource!(@product)
      end
    end

    def destroy
      authorize! :delete, Spree::Product
      @product = find_product(params[:id])
      @product.update_attribute(:deleted_at, Time.zone.now)
      @product.variants_including_master.update_all(deleted_at: Time.zone.now)
      render json: @product, serializer: Api::Admin::ProductSerializer, status: 204
    end

    # TODO: This should be named 'managed'. Is the action above used? Maybe we should remove it.
    def bulk_products
      product_query = OpenFoodNetwork::Permissions.new(current_api_user).
        editable_products.merge(product_scope)

      if params[:import_date].present?
        product_query = product_query.joins(:variants).merge(import_date_scope).group_by_products_id
      end

      @products = product_query.order('created_at DESC').
        ransack(params[:q]).result.
        page(params[:page]).per(params[:per_page])

      render_paged_products @products
    end

    def overridable
      producers = OpenFoodNetwork::Permissions.new(current_api_user).
        variant_override_producers.by_name

      @products = paged_products_for_producers producers

      render_paged_products @products
    end

    def soft_delete
      authorize! :delete, Spree::Product
      @product = find_product(params[:product_id])
      authorize! :delete, @product
      @product.destroy
      render json: @product, serializer: Api::Admin::ProductSerializer, status: 204
    end

    # POST /api/products/:product_id/clone
    #
    def clone
      authorize! :create, Spree::Product
      original_product = find_product(params[:product_id])
      authorize! :update, original_product

      @product = original_product.duplicate

      render json: @product, serializer: Api::Admin::ProductSerializer, status: 201
    end

    private

    # Copied and modified from SpreeApi::BaseController to allow
    # enterprise users to access inactive products
    def product_scope
      # This line modified
      if current_api_user.has_spree_role?("admin") || current_api_user.enterprises.present?
        scope = Spree::Product
        if params[:show_deleted]
          scope = scope.with_deleted
        end
      else
        scope = Spree::Product.active
      end

      scope.includes(:master)
    end

    def import_date_scope
      import_date = params[:import_date].to_datetime
      Spree::Variant.where(import_date: import_date..import_date + 24.hours)
    end

    def paged_products_for_producers(producers)
      Spree::Product.scoped.
        merge(product_scope).
        where(supplier_id: producers).
        by_producer.by_name.
        ransack(params[:q]).result.
        page(params[:page]).per(params[:per_page])
    end

    def render_paged_products(products)
      serializer = ActiveModel::ArraySerializer.new(
        products,
        each_serializer: Api::Admin::ProductSerializer
      )

      render text: {
        products: serializer,
        pagination: pagination_data(products)
      }.to_json
    end

    def pagination_data(results)
      {
        results: results.total_count,
        pages: results.num_pages,
        page: params[:page].to_i,
        per_page: params[:per_page].to_i
      }
    end
  end
end

{'fraction_non_alphanumeric': 0.09394547385813762, 'fraction_numerical': 0.0037767024666587987, 'mean_word_length': 2.9784037558685448, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3301419', 'n_tokens_mistral': 2483, 'n_tokens_neox': 2418, 'n_words': 516}