From 7fbe893927415e8c563511287131542d00f29e77 Mon Sep 17 00:00:00 2001 From: Jean-Baptiste Bellet Date: Wed, 29 Jun 2022 11:22:55 +0200 Subject: [PATCH 1/6] Add note to spree_orders object --- db/migrate/20220629080906_add_note_to_orders.rb | 5 +++++ db/schema.rb | 3 ++- 2 files changed, 7 insertions(+), 1 deletion(-) create mode 100644 db/migrate/20220629080906_add_note_to_orders.rb diff --git a/db/migrate/20220629080906_add_note_to_orders.rb b/db/migrate/20220629080906_add_note_to_orders.rb new file mode 100644 index 0000000000..3cb5415cf4 --- /dev/null +++ b/db/migrate/20220629080906_add_note_to_orders.rb @@ -0,0 +1,5 @@ +class AddNoteToOrders < ActiveRecord::Migration[6.1] + def change + add_column :spree_orders, :note, :string, null: false, default: "" + end +end diff --git a/db/schema.rb b/db/schema.rb index acee8ae142..7ce19f7723 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -10,7 +10,7 @@ # # It's strongly recommended that you check this file into your version control system. -ActiveRecord::Schema.define(version: 2022_06_21_230907) do +ActiveRecord::Schema.define(version: 2022_06_29_080906) do # These are extensions that must be enabled in order to support this database enable_extension "plpgsql" @@ -596,6 +596,7 @@ ActiveRecord::Schema.define(version: 2022_06_21_230907) do t.integer "created_by_id" t.decimal "included_tax_total", precision: 10, scale: 2, default: "0.0", null: false t.decimal "additional_tax_total", precision: 10, scale: 2, default: "0.0", null: false + t.string "note", default: "", null: false t.index ["completed_at", "user_id", "created_by_id", "created_at"], name: "spree_orders_completed_at_user_id_created_by_id_created_at_idx" t.index ["customer_id"], name: "index_spree_orders_on_customer_id" t.index ["distributor_id"], name: "index_spree_orders_on_distributor_id" From 3f1099d96839d7aef0973b404f496cb01b1a3dae Mon Sep 17 00:00:00 2001 From: Jean-Baptiste Bellet Date: Wed, 29 Jun 2022 11:23:50 +0200 Subject: [PATCH 2/6] Add edit note line on an order --- .../admin/spree/orders/shipments.js.erb | 3 +++ .../spree/orders/variant_autocomplete.js.erb | 6 +++++ app/views/spree/admin/orders/_form.html.haml | 1 + app/views/spree/admin/orders/_note.html.haml | 22 +++++++++++++++++++ app/webpacker/css/admin/orders.scss | 12 ++++++++++ config/locales/en.yml | 6 +++++ 6 files changed, 50 insertions(+) create mode 100644 app/views/spree/admin/orders/_note.html.haml diff --git a/app/assets/javascripts/admin/spree/orders/shipments.js.erb b/app/assets/javascripts/admin/spree/orders/shipments.js.erb index 75fcdcb93a..317df0d0d7 100644 --- a/app/assets/javascripts/admin/spree/orders/shipments.js.erb +++ b/app/assets/javascripts/admin/spree/orders/shipments.js.erb @@ -43,6 +43,9 @@ $(document).ready(function() { $('a.edit-tracking').click(toggleTrackingEdit); $('a.cancel-tracking').click(toggleTrackingEdit); + $('a.edit-note').click(toggleNoteEdit); + $('a.cancel-note').click(toggleNoteEdit); + handle_tracking_save = function(){ var link = $(this); var shipment_number = link.data('shipment-number'); diff --git a/app/assets/javascripts/admin/spree/orders/variant_autocomplete.js.erb b/app/assets/javascripts/admin/spree/orders/variant_autocomplete.js.erb index ea46231ece..094889d20a 100644 --- a/app/assets/javascripts/admin/spree/orders/variant_autocomplete.js.erb +++ b/app/assets/javascripts/admin/spree/orders/variant_autocomplete.js.erb @@ -145,6 +145,12 @@ toggleTrackingEdit = function(){ link.parents('tbody').find('tr.show-tracking').toggle(); } +toggleNoteEdit = function(){ + var link = $(this); + link.parents('tbody').find('tr.edit-note').toggle(); + link.parents('tbody').find('tr.show-note').toggle(); +} + toggleMethodEdit = function(){ var link = $(this); link.parents('tbody').find('tr.edit-method').toggle(); diff --git a/app/views/spree/admin/orders/_form.html.haml b/app/views/spree/admin/orders/_form.html.haml index 0e801912fd..4ec49a8d95 100644 --- a/app/views/spree/admin/orders/_form.html.haml +++ b/app/views/spree/admin/orders/_form.html.haml @@ -6,6 +6,7 @@ = render 'spree/admin/orders/insufficient_stock_lines', insufficient_stock_lines: @order.insufficient_stock_lines = render :partial => "spree/admin/orders/shipment", :collection => @order.shipments, :locals => { :order => order } + = render partial: "spree/admin/orders/note", locals: { order: @order } = render :partial => "spree/admin/orders/_form/adjustments", :locals => { :adjustments => @order.line_item_adjustments, :title => t(".line_item_adjustments")} = render :partial => "spree/admin/orders/_form/adjustments", :locals => { :adjustments => order_adjustments_for_display(@order), :title => t(".order_adjustments")} diff --git a/app/views/spree/admin/orders/_note.html.haml b/app/views/spree/admin/orders/_note.html.haml new file mode 100644 index 0000000000..b07d73978e --- /dev/null +++ b/app/views/spree/admin/orders/_note.html.haml @@ -0,0 +1,22 @@ +%table.index.edit-note-table + %tr.edit-note.hidden.total + %td{ :colspan => "5" } + %label + = t(".note_label") + = text_field_tag :note, @order.note + + %td.actions + = link_to '', '', class: 'save-note icon_link icon-ok no-text with-tip', data: { action: 'save' }, title: I18n.t('actions.save') + = link_to '', '', class: 'cancel-note icon_link icon-cancel no-text with-tip', data: { action: 'cancel' }, title: I18n.t('actions.cancel') + + %tr.show-note.total + %td{ :colspan => "5" } + - if order.note.present? + %strong + = t(".note_label") + = order.note + - else + = t(".no_note_present") + + %td.actions + = link_to '', '', class: 'edit-note icon_link icon-edit no-text with-tip', data: { action: 'edit' }, title: Spree.t('edit') diff --git a/app/webpacker/css/admin/orders.scss b/app/webpacker/css/admin/orders.scss index 8f5b724c35..7d067f0318 100644 --- a/app/webpacker/css/admin/orders.scss +++ b/app/webpacker/css/admin/orders.scss @@ -90,6 +90,18 @@ table.index td.actions { text-align: left; } +table.edit-note-table { + margin-top: -15px; + + tr:first-child th, tr:first-child td { + border-top: none; + } + + td.actions { + width: 15%; + } +} + .index-controls { button { diff --git a/config/locales/en.yml b/config/locales/en.yml index f86de538be..5d5a6c393c 100644 --- a/config/locales/en.yml +++ b/config/locales/en.yml @@ -838,6 +838,9 @@ en: variants_without_unit_value: "WARNING: Some variants do not have a unit value" all: "All" select_variant: "Select a variant" + note: + note_label: "Note:" + no_note_present: "No note provided." enterprise: select_outgoing_oc_products_from: Select outgoing OC products from @@ -3782,6 +3785,9 @@ See the %{link} to find out more about %{sitename}'s features and to start using from: "From" to: "Bill to" shipping: "Shipping" + note: + note_label: "Note:" + no_note_present: "No note provided." form: distribution_fields: title: "Distribution" From 90af6bd22da73ec64d053ce2c5935a3f8d991dfa Mon Sep 17 00:00:00 2001 From: Jean-Baptiste Bellet Date: Wed, 29 Jun 2022 11:24:21 +0200 Subject: [PATCH 3/6] Handle note saving with a new action on existing API controller --- .../admin/spree/orders/shipments.js.erb | 20 ++++++++++++++++++- app/controllers/api/v0/orders_controller.rb | 11 ++++++++++ config/routes/api.rb | 2 +- 3 files changed, 31 insertions(+), 2 deletions(-) diff --git a/app/assets/javascripts/admin/spree/orders/shipments.js.erb b/app/assets/javascripts/admin/spree/orders/shipments.js.erb index 317df0d0d7..d122365e3d 100644 --- a/app/assets/javascripts/admin/spree/orders/shipments.js.erb +++ b/app/assets/javascripts/admin/spree/orders/shipments.js.erb @@ -43,7 +43,7 @@ $(document).ready(function() { $('a.edit-tracking').click(toggleTrackingEdit); $('a.cancel-tracking').click(toggleTrackingEdit); - $('a.edit-note').click(toggleNoteEdit); + $('a.edit-note.icon-edit').click(toggleNoteEdit); $('a.cancel-note').click(toggleNoteEdit); handle_tracking_save = function(){ @@ -62,5 +62,23 @@ $(document).ready(function() { console.log(msg); }); } + + handle_note_save = function(){ + var link = $(this); + var note = link.parents('tbody').find('#note').val(); + var url = Spree.url( Spree.routes.orders_api + "/" + order_number); + + $.ajax({ + type: "PUT", + url: url, + data: { note: note } + }).done(function( msg ) { + window.location.reload(); + }).error(function( msg ) { + console.log(msg); + }); + } + $('[data-hook=admin_order_edit_form] a.save-tracking').click(handle_tracking_save); + $('[data-hook=admin_order_edit_form] a.save-note').click(handle_note_save); }); diff --git a/app/controllers/api/v0/orders_controller.rb b/app/controllers/api/v0/orders_controller.rb index 81e425d571..3f23a32e40 100644 --- a/app/controllers/api/v0/orders_controller.rb +++ b/app/controllers/api/v0/orders_controller.rb @@ -26,6 +26,13 @@ module Api } end + def update + authorize! :admin, order + + order.update!(order_params) + render json: order, serializer: Api::OrderDetailedSerializer, current_order: order + end + def ship authorize! :admin, order @@ -72,6 +79,10 @@ module Api includes(line_items: { variant: [:product, :stock_items, :default_price] }). first! end + + def order_params + params.permit(:note) + end end end end diff --git a/config/routes/api.rb b/config/routes/api.rb index 748c4ac563..f7bc47085e 100644 --- a/config/routes/api.rb +++ b/config/routes/api.rb @@ -18,7 +18,7 @@ Openfoodnetwork::Application.routes.draw do resources :variants, :only => [:index] - resources :orders, only: [:index, :show] do + resources :orders, only: [:index, :show, :update] do member do put :capture put :ship From 576faff3d7dc3ed6eeca389b7695be5c2eea1cf2 Mon Sep 17 00:00:00 2001 From: Jean-Baptiste Bellet Date: Thu, 30 Jun 2022 09:47:46 +0200 Subject: [PATCH 4/6] Spec: can edit/save note on an order --- spec/system/admin/order_spec.rb | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/spec/system/admin/order_spec.rb b/spec/system/admin/order_spec.rb index 98d187c37e..8f900d5fa3 100644 --- a/spec/system/admin/order_spec.rb +++ b/spec/system/admin/order_spec.rb @@ -525,6 +525,17 @@ describe ' expect(page).to have_content test_tracking_number end + it "can edit note" do + test_note = "this is a note" + expect(page).to_not have_content test_note + + find('.edit-note.icon-edit').click + fill_in "note", with: test_note + find('.save-note').click + + expect(page).to have_content test_note + end + it "viewing shipping fees" do shipping_fee = order.shipment_adjustments.first From de8c71d0984fa5b8dceb641765084ce8901ad425 Mon Sep 17 00:00:00 2001 From: Jean-Baptiste Bellet Date: Thu, 30 Jun 2022 15:37:33 +0200 Subject: [PATCH 5/6] Create a controller that handle a counter for an input text --- .../input_char_count_controller.js | 21 ++++++++++++ .../input_char_count_controller_test.js | 34 +++++++++++++++++++ 2 files changed, 55 insertions(+) create mode 100644 app/webpacker/controllers/input_char_count_controller.js create mode 100644 spec/javascripts/stimulus/input_char_count_controller_test.js diff --git a/app/webpacker/controllers/input_char_count_controller.js b/app/webpacker/controllers/input_char_count_controller.js new file mode 100644 index 0000000000..cafd93a673 --- /dev/null +++ b/app/webpacker/controllers/input_char_count_controller.js @@ -0,0 +1,21 @@ +import { Controller } from "stimulus"; + +export default class extends Controller { + static targets = ["count", "input"]; + + connect() { + this.inputTarget.addEventListener("keyup", this.countCharacters.bind(this)); + this.countCharacters(); + } + + countCharacters() { + this.displayCount( + this.inputTarget.value.length, + this.inputTarget.maxLength + ); + } + + displayCount(count, max) { + this.countTarget.textContent = `${count}/${max}`; + } +} diff --git a/spec/javascripts/stimulus/input_char_count_controller_test.js b/spec/javascripts/stimulus/input_char_count_controller_test.js new file mode 100644 index 0000000000..668531bfd1 --- /dev/null +++ b/spec/javascripts/stimulus/input_char_count_controller_test.js @@ -0,0 +1,34 @@ +/** + * @jest-environment jsdom + */ + +import { Application } from "stimulus"; +import input_char_count_controller from "../../../app/webpacker/controllers/input_char_count_controller"; + +describe("InputCharCountController", () => { + beforeAll(() => { + const application = Application.start(); + application.register("input-char-count", input_char_count_controller); + }); + + describe("default behavior", () => { + beforeEach(() => { + document.body.innerHTML = `
+ + +
`; + }); + + it("handle the content", () => { + const input = document.getElementById("input"); + const count = document.getElementById("count"); + // Default value + expect(count.textContent).toBe("5/280"); + + input.value = "Hello world"; + input.dispatchEvent(new Event("keyup")); + + expect(count.textContent).toBe("11/280"); + }); + }); +}); From 89809aed5fdcd953d13b9108290c942a5182ceb4 Mon Sep 17 00:00:00 2001 From: Jean-Baptiste Bellet Date: Thu, 30 Jun 2022 15:37:55 +0200 Subject: [PATCH 6/6] Add counter on note input --- app/views/spree/admin/orders/_note.html.haml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/app/views/spree/admin/orders/_note.html.haml b/app/views/spree/admin/orders/_note.html.haml index b07d73978e..d5b2df2d38 100644 --- a/app/views/spree/admin/orders/_note.html.haml +++ b/app/views/spree/admin/orders/_note.html.haml @@ -1,9 +1,10 @@ %table.index.edit-note-table %tr.edit-note.hidden.total - %td{ :colspan => "5" } + %td{ colspan: "5", data: { controller: "input-char-count" }, style: "position: relative;" } %label = t(".note_label") - = text_field_tag :note, @order.note + = text_field_tag :note, @order.note, { maxLength: 280, data: { "input-char-count-target": "input" } } + %span.edit-note-count{ data: { "input-char-count-target": "count" }, style: "position: absolute; right: 7px; top: 7px; font-size: 11px;" } %td.actions = link_to '', '', class: 'save-note icon_link icon-ok no-text with-tip', data: { action: 'save' }, title: I18n.t('actions.save')