From 68da9c9e04c9981e08229f4029b2379ee2f071ab Mon Sep 17 00:00:00 2001 From: David Cook Date: Mon, 3 Jun 2024 17:39:44 +1000 Subject: [PATCH] Add form to save column preferences --- .../admin/column_preferences_controller.rb | 35 ++++++++--- app/views/admin/products_v3/_sort.html.haml | 14 +++++ config/locales/en.yml | 3 +- .../column_preference_defaults.rb | 19 ++++++ .../column_preferences_controller_spec.rb | 58 ++++++++++++++----- .../system/admin/products_v3/products_spec.rb | 5 ++ 6 files changed, 112 insertions(+), 22 deletions(-) diff --git a/app/controllers/admin/column_preferences_controller.rb b/app/controllers/admin/column_preferences_controller.rb index 688dfdb750..3f405cfd90 100644 --- a/app/controllers/admin/column_preferences_controller.rb +++ b/app/controllers/admin/column_preferences_controller.rb @@ -4,17 +4,23 @@ module Admin class ColumnPreferencesController < Admin::ResourceController before_action :load_collection, only: [:bulk_update] - respond_to :json - def bulk_update @cp_set.collection.each { |cp| authorize! :bulk_update, cp } if @cp_set.save - render json: @cp_set.collection, each_serializer: Api::Admin::ColumnPreferenceSerializer + respond_to do |format| + format.json { render json: @cp_set.collection, each_serializer: Api::Admin::ColumnPreferenceSerializer } + format.html { render inline: "saved" } #todo + end elsif @cp_set.errors.present? - render json: { errors: @cp_set.errors }, status: :bad_request + respond_to do |format| + format.json { render json: { errors: @cp_set.errors }, status: :bad_request } + format.html { render inline: "errors" } #todo + end else - render body: nil, status: :internal_server_error + respond_to do |format| + format.all { render body: nil, status: :internal_server_error } + end end end @@ -28,9 +34,22 @@ module Admin end def load_collection - collection_attributes = Hash[permitted_params[:column_preferences]. - each_with_index.map { |cp, i| [i, cp] }] - collection_attributes.select!{ |_i, cp| cp[:action_name] == permitted_params[:action_name] } + collection_attributes = nil + + respond_to do |format| + format.json do + collection_attributes = Hash[permitted_params[:column_preferences]. + each_with_index.map { |cp, i| [i, cp] }] + collection_attributes.select!{ |_i, cp| cp[:action_name] == permitted_params[:action_name] } + end + format.html do + # Inject action name and user ID for each column_preference + collection_attributes = permitted_params[:column_preferences].to_h.each_value { |cp| + cp[:action_name] = permitted_params[:action_name] + cp[:user_id] = spree_current_user.id + } + end + end @cp_set = Sets::ColumnPreferenceSet.new(@column_preferences, collection_attributes:) end diff --git a/app/views/admin/products_v3/_sort.html.haml b/app/views/admin/products_v3/_sort.html.haml index f53eec4e76..a8a3f1b335 100644 --- a/app/views/admin/products_v3/_sort.html.haml +++ b/app/views/admin/products_v3/_sort.html.haml @@ -13,3 +13,17 @@ options_for_select([15, 25, 50, 100].collect{|i| [t('.pagination.per_page.per_page', num: i), i]}, pagy&.items), class: "no-input per-page", data: { controller: "tom-select search", action: "change->search#changePerPage", "tom-select-options-value": '{ "plugins": [] }'} + + / Columns dropdown + = form_with url: bulk_update_admin_column_preferences_path, method: :put do |f| + = hidden_field_tag :action_name, "#{controller_name}_#{action_name}" + + - ColumnPreference.for(spree_current_user, "#{controller_name}_#{action_name}").each do |column_preference| + = f.fields_for("column_preferences[]", column_preference) do |cp_form| + = cp_form.hidden_field :id + = cp_form.hidden_field :column_name + %label + = cp_form.check_box :visible + = t("admin.products_page.columns." + column_preference.column_name) + + = f.submit t('admin.column_save_as_default') diff --git a/config/locales/en.yml b/config/locales/en.yml index 47b4b07814..41c76b2cc8 100644 --- a/config/locales/en.yml +++ b/config/locales/en.yml @@ -571,6 +571,7 @@ en: per_page: "%{count} items per page" colums: Columns columns: + image: Image name: Name unit_scale: Unit scale unit: Unit @@ -661,7 +662,7 @@ en: choose: "Choose..." please_select: Please select... - column_save_as_default: Save As Default + column_save_as_default: Save as default columns: Columns actions: Actions viewing: "Viewing: %{current_view_name}" diff --git a/lib/open_food_network/column_preference_defaults.rb b/lib/open_food_network/column_preference_defaults.rb index 9bb09b2061..39fc0edf69 100644 --- a/lib/open_food_network/column_preference_defaults.rb +++ b/lib/open_food_network/column_preference_defaults.rb @@ -77,6 +77,25 @@ module OpenFoodNetwork } end + def products_v3_index_columns + # TODO: Use consistent translation keys + node = "admin.products_page.columns" + { + image: { name: I18n.t("admin.image"), visible: true }, + producer: { name: I18n.t("admin.producer"), visible: true }, + sku: { name: I18n.t("admin.sku"), visible: false }, + name: { name: I18n.t("admin.name"), visible: true }, + unit: { name: I18n.t("#{node}.unit"), visible: true }, + price: { name: I18n.t("admin.price"), visible: true }, + on_hand: { name: I18n.t("admin.on_hand"), visible: true }, + on_demand: { name: I18n.t("admin.on_demand"), visible: true }, + category: { name: I18n.t("#{node}.category"), visible: false }, + tax_category: { name: I18n.t("#{node}.tax_category"), visible: false }, + inherits_properties: { name: I18n.t("#{node}.inherits_properties"), visible: false }, + import_date: { name: I18n.t("#{node}.import_date"), visible: false } + } + end + def enterprises_index_columns node = "admin.enterprises.index" { diff --git a/spec/controllers/admin/column_preferences_controller_spec.rb b/spec/controllers/admin/column_preferences_controller_spec.rb index 41f34b163e..5cd8707bb0 100644 --- a/spec/controllers/admin/column_preferences_controller_spec.rb +++ b/spec/controllers/admin/column_preferences_controller_spec.rb @@ -9,13 +9,26 @@ RSpec.describe Admin::ColumnPreferencesController, type: :controller do let!(:user1) { create(:user) } let!(:user2) { create(:user) } let!(:enterprise) { create(:enterprise, owner: user1, users: [user1, user2]) } + let!(:column_preference) { + ColumnPreference.create(user_id: user1.id, action_name: 'enterprises_index', + column_name: "name", visible: true) + } + + shared_examples "where I own the preferences submitted" do + before do + allow(controller).to receive(:spree_current_user) { user1 } + end + + it "allows me to update the column preferences" do + spree_put :bulk_update, format: request_format, action_name: "enterprises_index", + column_preferences: column_preference_params + expect(ColumnPreference.where(user_id: user1.id, + action_name: 'enterprises_index').count).to be 3 + end + end context "json" do - let!(:column_preference) { - ColumnPreference.create(user_id: user1.id, action_name: 'enterprises_index', - column_name: "name", visible: true) - } - + let(:request_format) { :json } let(:column_preference_params) { [ { id: column_preference.id, user_id: user1.id, action_name: "enterprises_index", @@ -27,28 +40,47 @@ RSpec.describe Admin::ColumnPreferencesController, type: :controller do ] } + it_behaves_like "where I own the preferences submitted" + context "where I don't own the preferences submitted" do before do allow(controller).to receive(:spree_current_user) { user2 } end it "prevents me from updating the column preferences" do - spree_put :bulk_update, format: :json, action_name: "enterprises_index", + spree_put :bulk_update, format: request_format, action_name: "enterprises_index", column_preferences: column_preference_params expect(ColumnPreference.count).to be 1 end end + end - context "where I own the preferences submitted" do + context "html" do + let(:request_format) { :html } + let(:column_preference_params) { + { + '0': { id: column_preference.id, column_name: "name", visible: "0" }, + '1': { id: nil, column_name: "producer", visible: "1" }, + '2': { id: nil, column_name: "status", visible: "1" }, + } + } + + it_behaves_like "where I own the preferences submitted" + + context "where I don't own the preferences submitted" do before do - allow(controller).to receive(:spree_current_user) { user1 } + allow(controller).to receive(:spree_current_user) { user2 } end - it "allows me to update the column preferences" do - spree_put :bulk_update, format: :json, action_name: "enterprises_index", - column_preferences: column_preference_params - expect(ColumnPreference.where(user_id: user1.id, - action_name: 'enterprises_index').count).to be 3 + # This has the same effect as the JSON action, but due to differing implementation, + # it has different expections. + it "prevents me from updating the column preferences" do + expect { + spree_put :bulk_update, format: request_format, action_name: "enterprises_index", + column_preferences: column_preference_params + }.to raise_error(ActiveRecord::RecordNotUnique) + + expect(column_preference.reload.visible).to eq true end end end diff --git a/spec/system/admin/products_v3/products_spec.rb b/spec/system/admin/products_v3/products_spec.rb index 9f9ee35ecd..73db0e4bca 100644 --- a/spec/system/admin/products_v3/products_spec.rb +++ b/spec/system/admin/products_v3/products_spec.rb @@ -43,6 +43,11 @@ RSpec.describe 'As an enterprise user, I can manage my products', feature: :admi expect(page).to have_selector "th", text: "Price" expect(page).to have_selector "th", text: "On Hand" + uncheck "Name" + click_on "Save as default" + refresh + expect(page).to have_unchecked_field "Name" + pending "Pending implementation, issue #11055" toggle_columns /^.{0,1}Producer$/i