diff --git a/app/serializers/api/admin/enterprise_serializer.rb b/app/serializers/api/admin/enterprise_serializer.rb index f189e57fd01..7c29b41e708 100644 --- a/app/serializers/api/admin/enterprise_serializer.rb +++ b/app/serializers/api/admin/enterprise_serializer.rb @@ -15,7 +15,7 @@ class EnterpriseSerializer < ActiveModel::Serializer :terms_and_conditions_file_name, :terms_and_conditions_updated_at, :preferred_invoice_order_by_supplier, :preferred_product_low_stock_display, :visible, :hide_ofn_navigation, :white_label_logo, - :white_label_logo_link + :white_label_logo_link, :external_billing_id has_one :owner, serializer: Api::Admin::UserSerializer has_many :users, serializer: Api::Admin::UserSerializer diff --git a/app/services/permitted_attributes/enterprise.rb b/app/services/permitted_attributes/enterprise.rb index 234fadac77a..1dd5b5a8385 100644 --- a/app/services/permitted_attributes/enterprise.rb +++ b/app/services/permitted_attributes/enterprise.rb @@ -37,7 +37,7 @@ def self.basic_permitted_attributes :preferred_invoice_order_by_supplier, :preferred_product_low_stock_display, :hide_ofn_navigation, :white_label_logo, :white_label_logo_link, - :hide_groups_tab + :hide_groups_tab, :external_billing_id, ] end end diff --git a/app/views/admin/enterprises/form/_primary_details.html.haml b/app/views/admin/enterprises/form/_primary_details.html.haml index 04609e9b586..e5bbf4eed06 100644 --- a/app/views/admin/enterprises/form/_primary_details.html.haml +++ b/app/views/admin/enterprises/form/_primary_details.html.haml @@ -16,24 +16,8 @@ %label= t('.primary_producer') = render partial: 'admin/shared/whats_this_tooltip', locals: {tooltip_text: t('.primary_producer_tip')} .five.columns.omega - = f.check_box :is_primary_producer, data: { action: "change->primary-details#primaryProducerChanged" } + = f.check_box :is_primary_producer, data: { action: "change->primary-details#primaryProducerChanged" } = f.label :is_primary_producer, t('.producer') -- if spree_current_user.admin? - .row - .three.columns.alpha - = f.label :sells, t('.sells') - = render partial: 'admin/shared/whats_this_tooltip', locals: {tooltip_text: t('.sells_tip')} - .two.columns - = f.radio_button :sells, "none", 'ng-model' => 'Enterprise.sells', data: {action: "change->primary-details#enterpriseSellsChanged"} - = f.label :sells, t('.none'), value: "none" - .two.columns - = f.radio_button :sells, "own", 'ng-model' => 'Enterprise.sells', data: {action: "change->primary-details#enterpriseSellsChanged"} - = f.label :sells, t('.own'), value: "own" - .four.columns.omega - = f.radio_button :sells, "any", 'ng-model' => 'Enterprise.sells', data: {action: "change->primary-details#enterpriseSellsChanged"} - = f.label :sells, t('.any'), value: "any" - %span{ style: "width: 30px; height: 30px;", class: "hidden", data: { "primary-details-target": "spinner" } } - = render partial: "components/admin_spinner" .row .three.columns.alpha %label= t('.visible_in_search') @@ -49,3 +33,29 @@ = f.label :visible, t('.hidden'), value: 'hidden' = render partial: 'admin/enterprises/form/permalink' + +- if spree_current_user.admin? + .row + %fieldset.alpha.no-border-bottom + %legend= t('.admin_only_legend') + .row + .three.columns.alpha + = f.label :sells, t('.sells') + = render partial: 'admin/shared/whats_this_tooltip', locals: {tooltip_text: t('.sells_tip')} + .two.columns + = f.radio_button :sells, "none", 'ng-model' => 'Enterprise.sells', data: {action: "change->primary-details#enterpriseSellsChanged"} + = f.label :sells, t('.none'), value: "none" + .two.columns + = f.radio_button :sells, "own", 'ng-model' => 'Enterprise.sells', data: {action: "change->primary-details#enterpriseSellsChanged"} + = f.label :sells, t('.own'), value: "own" + .four.columns.omega + = f.radio_button :sells, "any", 'ng-model' => 'Enterprise.sells', data: {action: "change->primary-details#enterpriseSellsChanged"} + = f.label :sells, t('.any'), value: "any" + %span{ style: "width: 30px; height: 30px;", class: "hidden", data: { "primary-details-target": "spinner" } } + = render partial: "components/admin_spinner" + .row + .three.columns.alpha + = f.label :external_billing_id, t('.external_billing_id') + = render partial: 'admin/shared/whats_this_tooltip', locals: {tooltip_text: t('.external_billing_id_tip')} + .four.columns + = f.text_field :external_billing_id, { placeholder: t('.external_billing_id_placeholder') } diff --git a/config/locales/en.yml b/config/locales/en.yml index 6c8fa2dbdcf..a1a5bb33c73 100644 --- a/config/locales/en.yml +++ b/config/locales/en.yml @@ -1284,11 +1284,15 @@ en: own: Own sells: Sells sells_tip: "None - enterprise does not sell to customers directly.
Own - Enterprise sells own products to customers.
Any - Enterprise can sell own or other enterprises products.
" + external_billing_id: External Billing ID + external_billing_id_placeholder: eg. INV-2024-123456 + external_billing_id_tip: "This is the ID used by the external billing system to identify this enterprise." visible_in_search: Visible in search? visible_in_search_tip: "Shops can be
1. publicly visible, appearing on the OFN map and listings.
2. Hidden on maps and listings but referenced by other shops and linked in their profile.
3. Completely hidden." visible: Public not_visible: Hidden hidden: Hide all references + admin_only_legend: Admin only properties: legend: "Properties" permalink: @@ -3193,6 +3197,7 @@ See the %{link} to find out more about %{sitename}'s features and to start using report_header_hub_code: Hub Code report_header_hub_id: Hub ID report_header_hub_business_number: "Hub Business Number" + report_header_hub_external_billing_id: "Hub External Billing Id" report_header_hub_legal_name: "Hub Legal Name" report_header_hub_contact_name: "Hub Contact Name" report_header_hub_email: "Hub Public Email" diff --git a/db/migrate/20241113185651_add_external_billing_id_on_enterprises.rb b/db/migrate/20241113185651_add_external_billing_id_on_enterprises.rb new file mode 100644 index 00000000000..bd0292bbe3d --- /dev/null +++ b/db/migrate/20241113185651_add_external_billing_id_on_enterprises.rb @@ -0,0 +1,5 @@ +class AddExternalBillingIdOnEnterprises < ActiveRecord::Migration[7.0] + def change + add_column :enterprises, :external_billing_id, :string, limit: 128 + end +end diff --git a/db/schema.rb b/db/schema.rb index be371a9499d..37bab4a1e64 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[7.0].define(version: 2024_11_12_230401) do +ActiveRecord::Schema[7.0].define(version: 2024_11_13_185651) do # These are extensions that must be enabled in order to support this database enable_extension "pg_stat_statements" enable_extension "plpgsql" @@ -229,6 +229,7 @@ t.boolean "hide_ofn_navigation", default: false, null: false t.text "white_label_logo_link" t.boolean "hide_groups_tab", default: false + t.string "external_billing_id", limit: 128 t.index ["address_id"], name: "index_enterprises_on_address_id" t.index ["is_primary_producer", "sells"], name: "index_enterprises_on_is_primary_producer_and_sells" t.index ["name"], name: "index_enterprises_on_name", unique: true diff --git a/lib/reporting/reports/revenues_by_hub/base.rb b/lib/reporting/reports/revenues_by_hub/base.rb index e539c77fed2..8b10386a6f2 100644 --- a/lib/reporting/reports/revenues_by_hub/base.rb +++ b/lib/reporting/reports/revenues_by_hub/base.rb @@ -24,6 +24,7 @@ def columns # rubocop:disable Metrics/AbcSize hub: proc { |orders| distributor(orders).name }, hub_id: proc { |orders| distributor(orders).id }, hub_business_number: proc { |orders| distributor(orders).abn }, + hub_external_billing_id: proc { |orders| distributor(orders).external_billing_id }, hub_legal_name: proc { |orders| distributor(orders).business_address&.company }, hub_contact_name: proc { |orders| distributor(orders).contact_name }, hub_email: proc { |orders| distributor(orders).email_address }, diff --git a/spec/controllers/admin/enterprises_controller_spec.rb b/spec/controllers/admin/enterprises_controller_spec.rb index 4caf3e38d79..415f75cc2a5 100644 --- a/spec/controllers/admin/enterprises_controller_spec.rb +++ b/spec/controllers/admin/enterprises_controller_spec.rb @@ -409,6 +409,16 @@ distributor.reload expect(distributor.users).to include user end + + it "allows 'external_billing_id' to be changed" do + allow(controller).to receive_messages spree_current_user: admin_user + enterprise_params = + { id: profile_enterprise, enterprise: { external_billing_id: 'INV123456' } } + + spree_put :update, enterprise_params + profile_enterprise.reload + expect(profile_enterprise.external_billing_id).to eq 'INV123456' + end end context "geocoding" do diff --git a/spec/controllers/api/v0/enterprises_controller_spec.rb b/spec/controllers/api/v0/enterprises_controller_spec.rb index d0529f3eeba..55fd6a2a158 100644 --- a/spec/controllers/api/v0/enterprises_controller_spec.rb +++ b/spec/controllers/api/v0/enterprises_controller_spec.rb @@ -7,6 +7,30 @@ let(:enterprise) { create(:distributor_enterprise) } + context "as an admin user" do + let(:admin) { create(:admin_user) } + let!(:enterprise) { create(:distributor_enterprise) } + + before do + allow(controller).to receive(:spree_current_user) { admin } + end + + describe "updating an enterprise" do + let(:enterprise_params) do + { + external_billing_id: 'INV123456' + } + end + + it "changes the external_billing_id field" do + api_put :update, id: enterprise.id, enterprise: enterprise_params + expect(response.status).to eq 200 + + expect(enterprise.reload.external_billing_id).to eq('INV123456') + end + end + end + context "as an enterprise owner" do let(:enterprise_owner) { create(:user) } let!(:enterprise) { create(:distributor_enterprise, owner: enterprise_owner) } diff --git a/spec/serializers/api/admin/enterprise_serializer_spec.rb b/spec/serializers/api/admin/enterprise_serializer_spec.rb index 3f20145771f..8483c2e27c9 100644 --- a/spec/serializers/api/admin/enterprise_serializer_spec.rb +++ b/spec/serializers/api/admin/enterprise_serializer_spec.rb @@ -5,10 +5,11 @@ RSpec.describe Api::Admin::EnterpriseSerializer do include FileHelper - let(:enterprise) { create(:distributor_enterprise) } + let(:enterprise) { create(:distributor_enterprise, external_billing_id: 'INV123456') } it "serializes an enterprise" do serializer = Api::Admin::EnterpriseSerializer.new enterprise expect(serializer.to_json).to match enterprise.name + expect(serializer.as_json[:external_billing_id]).to eq('INV123456') end context "for logo" do diff --git a/spec/system/admin/reports/revenues_by_hub_spec.rb b/spec/system/admin/reports/revenues_by_hub_spec.rb index 079a94d2fa2..9834fc55ba0 100644 --- a/spec/system/admin/reports/revenues_by_hub_spec.rb +++ b/spec/system/admin/reports/revenues_by_hub_spec.rb @@ -37,9 +37,9 @@ tax_rate_name: "Tax 1" ) end - let(:distributor1) { create(:enterprise, name: "Hub 1", owner:) } + let(:distributor1) { create(:enterprise, name: "Hub 1", owner:, external_billing_id: 'INV1234') } let(:distributor2) { create(:enterprise, name: "Hub 2", owner:) } - let(:distributor3) { create(:enterprise, name: "Hub 3", owner:) } + let(:distributor3) { create(:enterprise, name: "Hub 3", owner:, external_billing_id: 'INV4321') } let(:owner) { create(:user, email: 'email@email.com') } let(:order_cycle) { create(:simple_order_cycle) } let(:product) { create(:product) } @@ -64,6 +64,7 @@ "Hub", "Hub ID", "Hub Business Number", + "Hub External Billing Id", "Hub Legal Name", "Hub Contact Name", "Hub Public Email", @@ -86,6 +87,7 @@ "Hub 1", order.distributor.id, "none", + "INV1234", "none", "none", "none", @@ -110,6 +112,7 @@ "none", "none", "none", + "none", "email@email.com", "none", "10 Lovely Street", @@ -128,6 +131,7 @@ "Hub 3", order_with_voucher_tax_excluded.distributor.id, "none", + "INV4321", "none", "none", "none",