cats_core 1.4.45 → 1.4.49

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 710ffdc5b10d0f97aa5f40aaa8e67a99eaea21120c0b96894d46f86a47b10312
4
- data.tar.gz: 3c1b7594b8717c668bb9f38d481afa54057005f524171bd3c088fdf6047344b2
3
+ metadata.gz: '08b9c239346db9904b66db3df8c7c3461f5c3766c6739b3a039cbc96e3d7fa2e'
4
+ data.tar.gz: 4838b7d3720606e0581d364888771a39ec2c3c69c164bfebe838e2d8faac9314
5
5
  SHA512:
6
- metadata.gz: 4b522fa9d586d12f3255b0a9044caff4c8b694e336e3b284a657bc14d2f10a0e10ad3fce4d082784b65435bd73c396b8a593c6c7630bc90b9ac1388bf6f51915
7
- data.tar.gz: 46fbc7ca6360f71e4f6cc992f03a3711b302f2f351c7dca8996999cee8c8eaf196321324bf9ed3f6bf16940c04f5224c72bd5124147663a7b4533aeddd9f27bd
6
+ metadata.gz: 915436bd0e4a48d08809aedc9cbd6317c89ed6c45d2d2356f75805c41f7abb2c756173b0140a84ecad77cf2483058f42106eb31d692f75f80b874c555b59b060
7
+ data.tar.gz: 324ca7a987fbda8bb7dd50e06c84daeeb58acf0743335f8ce39296dcde740b54503e8caca431b159984b59ad678061c3586838e8607f9dadb12581bf972b289c
@@ -25,11 +25,22 @@ module Cats
25
25
  render json: { success: true, data: serialize(woredas) }
26
26
  end
27
27
 
28
+ def create_fdp
29
+ service = LocationService.new
30
+ p = fdp_params
31
+ fdp = service.create_fdp(p[:code], p[:name], p[:parent_id], p[:description])
32
+ render json: { success: true, data: serialize(fdp) }
33
+ end
34
+
28
35
  private
29
36
 
30
37
  def model_params
31
38
  params.require(:payload).permit(:code, :name, :location_type, :description, :parent_id)
32
39
  end
40
+
41
+ def fdp_params
42
+ params.require(:payload).permit(:code, :name, :description, :parent_id)
43
+ end
33
44
  end
34
45
  end
35
46
  end
@@ -4,28 +4,60 @@ module Cats
4
4
  include Common
5
5
 
6
6
  def index
7
- stores = Store.includes(:store_keeper, :stacks).where(warehouse_id: params[:id])
7
+ stores = Store.includes(:stacks).where(warehouse_id: params[:id])
8
8
  render json: { success: true, data: serialize(stores) }
9
9
  end
10
10
 
11
11
  def filter
12
- query = Store.includes(:store_keeper, :stacks).ransack(params[:q])
12
+ query = Store.includes(:stacks).ransack(params[:q])
13
13
  render json: { success: true, data: serialize(query.result) }
14
14
  end
15
15
 
16
16
  def stores_for_hub
17
17
  warehouses = Location.find(params[:id]).children
18
18
  ids = warehouses.map(&:id)
19
- stores = Store.includes(:store_keeper, :stacks).where(warehouse_id: ids)
19
+ stores = Store.includes(:stacks).where(warehouse_id: ids)
20
20
  render json: { success: true, data: serialize(stores) }
21
21
  end
22
22
 
23
+ def assign_store
24
+ store_keeper = User.find(params[:id])
25
+ store_keeper.details['stores'] ||= []
26
+ store_keeper.details['stores'] += store_params[:store_ids]
27
+ store_keeper.save!
28
+ render json: { success: true, data: serialize(store_keeper) }
29
+ end
30
+
31
+ def unassign_store
32
+ store_keeper = User.find(params[:id])
33
+ if store_keeper.details.key?('stores')
34
+ store_keeper.details['stores'] -= store_params[:store_ids]
35
+ store_keeper.save!
36
+ render json: { success: true, data: serialize(store_keeper) }
37
+ else
38
+ render json: { success: false, error: 'User has no stores assigned.' }
39
+ end
40
+ end
41
+
42
+ def fdp
43
+ store = Store.find(params[:id])
44
+ location = store.warehouse.parent
45
+ if location.location_type == Location::FDP
46
+ render json: { success: true, data: serialize(location) }
47
+ else
48
+ render json: { success: false, error: 'No FDP is associated with store.' }
49
+ end
50
+ end
51
+
23
52
  private
24
53
 
25
54
  def model_params
26
55
  params.require('payload').permit(:id, :code, :name, :length, :width, :height, :temporary, :has_gangway,
27
- :gangway_length, :gangway_width, :gangway_corner_dist, :warehouse_id,
28
- :store_keeper_id)
56
+ :gangway_length, :gangway_width, :gangway_corner_dist, :warehouse_id)
57
+ end
58
+
59
+ def store_params
60
+ params.require(:payload).permit(store_ids: [])
29
61
  end
30
62
  end
31
63
  end
@@ -60,7 +60,7 @@ module Cats
60
60
  def name
61
61
  # For this to be efficient, our query should use includes like
62
62
  # Commodity.includes(project: { source: commodity_category })
63
- project.source.commodity_category.name
63
+ project.source.commodity_name
64
64
  end
65
65
 
66
66
  def validate_updateability
@@ -75,6 +75,21 @@ module Cats
75
75
  def start
76
76
  self.dispatch_status = STARTED
77
77
  save!
78
+
79
+ # Check if destination is an FDP and create receipt authorization
80
+ location = dispatch_plan_item.destination
81
+ authorized_by = User.find_by(first_name: 'SYSTEM-USER')
82
+ return unless location.location_type == Location::FDP
83
+
84
+ store = location.fdp_store
85
+ ReceiptAuthorization.create!(
86
+ dispatch: self,
87
+ store: store,
88
+ quantity: quantity,
89
+ received_quantity: 0,
90
+ status: Authorization::AUTHORIZED,
91
+ authorized_by: authorized_by
92
+ )
78
93
  end
79
94
 
80
95
  def receive
@@ -5,11 +5,10 @@ module Cats
5
5
  ZONE = 'Zone'.freeze
6
6
  WOREDA = 'Woreda'.freeze
7
7
  FDP = 'Fdp'.freeze
8
- KEBELE = 'Kebele'.freeze
9
8
  HUB = 'Hub'.freeze
10
9
  WAREHOUSE = 'Warehouse'.freeze
11
10
 
12
- LOCATION_TYPES = [REGION, ZONE, WOREDA, KEBELE, HUB, WAREHOUSE, FDP].freeze
11
+ LOCATION_TYPES = [REGION, ZONE, WOREDA, FDP, HUB, WAREHOUSE].freeze
13
12
 
14
13
  has_ancestry
15
14
 
@@ -23,10 +22,9 @@ module Cats
23
22
  REGION => [],
24
23
  ZONE => [REGION],
25
24
  WOREDA => [REGION, ZONE],
26
- KEBELE => [REGION, ZONE, WOREDA],
27
25
  FDP => [REGION, ZONE, WOREDA],
28
- HUB => [REGION, ZONE, WOREDA, KEBELE],
29
- WAREHOUSE => [REGION, ZONE, WOREDA, KEBELE, HUB]
26
+ HUB => [REGION, ZONE, WOREDA, FDP],
27
+ WAREHOUSE => [REGION, ZONE, WOREDA, FDP, HUB]
30
28
  }
31
29
 
32
30
  return if location_type.nil? || location_type.empty?
@@ -46,6 +44,12 @@ module Cats
46
44
  # wrong type of parent to our location.
47
45
  errors.add(:location, "cannot have #{parent.location_type} as parent")
48
46
  end
47
+
48
+ def fdp_store
49
+ return nil unless location_type == FDP
50
+
51
+ Store.find_by(code: "FDP-ST-#{code}")
52
+ end
49
53
  end
50
54
  end
51
55
  end
@@ -21,7 +21,8 @@ module Cats
21
21
  validates :stack_status, inclusion: { in: STACK_STATUSES }
22
22
  validate :validate_coordinates, :validate_dimensions, :validate_distance_from_wall, :validate_overlap,
23
23
  :validate_space_between_stack, :validate_max_height, :validate_max_length, :validate_max_width,
24
- :validate_distance_from_ceiling, unless: -> { store && store.code == 'SUP-STORE' }
24
+ :validate_distance_from_ceiling,
25
+ unless: -> { store && (store.code == 'SUP-STORE' || store.code.start_with?('FDP-ST')) }
25
26
 
26
27
  delegate :batch_no, to: :commodity, prefix: true
27
28
 
@@ -2,7 +2,6 @@ module Cats
2
2
  module Core
3
3
  class Store < ApplicationRecord
4
4
  belongs_to :warehouse, class_name: 'Cats::Core::Location'
5
- belongs_to :store_keeper, class_name: 'Cats::Core::User'
6
5
  has_many :stacks
7
6
 
8
7
  validates :code, :name, :length, :width, :height, presence: true
@@ -17,7 +16,6 @@ module Cats
17
16
  validate :validate_location
18
17
 
19
18
  before_create :update_usable_space
20
- after_save :update_store_keeper
21
19
 
22
20
  def validate_location
23
21
  return if warehouse.nil?
@@ -25,33 +23,11 @@ module Cats
25
23
  errors.add(:warehouse, 'must be a valid warehouse') unless warehouse.location_type == Location::WAREHOUSE
26
24
  end
27
25
 
28
- def store_keeper_name
29
- "#{store_keeper.first_name} #{store_keeper.last_name}"
30
- end
31
-
32
26
  def update_usable_space
33
27
  self.usable_space = (length - 2) * (width - 2)
34
28
  self.usable_space -= (gangway_length * gangway_width) if has_gangway
35
29
  self.available_space = self.usable_space
36
30
  end
37
-
38
- def update_store_keeper
39
- return unless store_keeper_id_previously_changed?
40
-
41
- unless id_previously_changed?
42
- old_storekeeper = Cats::Core::User.find(store_keeper_id_previously_was)
43
- old_storekeeper.details['stores'].delete(id)
44
- old_storekeeper.save
45
- end
46
- if store_keeper.details.key?('stores')
47
- store_keeper.details['stores'] << id
48
- else
49
- store_keeper.details['stores'] = [id]
50
- end
51
- store_keeper.save
52
- end
53
-
54
- delegate(:phone_number, to: :store_keeper, prefix: true)
55
31
  end
56
32
  end
57
33
  end
@@ -1,9 +1,8 @@
1
1
  module Cats
2
2
  module Core
3
3
  class StoreSerializer < ActiveModel::Serializer
4
- attributes :id, :code, :name, :store_keeper_name, :store_keeper_phone_number, :length, :width, :height,
5
- :temporary, :has_gangway, :gangway_length, :gangway_width, :gangway_corner_dist, :warehouse_id,
6
- :store_keeper_id
4
+ attributes :id, :code, :name, :length, :width, :height, :temporary, :has_gangway, :gangway_length,
5
+ :gangway_width, :gangway_corner_dist, :warehouse_id
7
6
 
8
7
  has_many :stacks
9
8
  end
@@ -24,9 +24,42 @@ module Cats
24
24
  statuses = authorization.dispatch.receipt_authorizations.map(&:driver_confirmed).uniq
25
25
  authorization.dispatch.receive if statuses.length == 1 && statuses[0]
26
26
 
27
+ # Create destination stack and transaction for FDP
28
+ location = authorization.dispatch.dispatch_plan_item.destination
29
+ if location.location_type == Location::FDP
30
+ create_stack(authorization_id)
31
+ stack(authorization_id)
32
+ end
33
+
27
34
  authorization
28
35
  end
29
36
 
37
+ # A method to create stack and stack transactions for FDP
38
+ def create_stack(authorization_id)
39
+ authorization = ReceiptAuthorization.find(authorization_id)
40
+ commodity = authorization.dispatch.dispatch_plan_item.commodity
41
+ stack = Stack.create!(
42
+ code: commodity.batch_no,
43
+ length: 100,
44
+ width: 100,
45
+ height: 100,
46
+ start_x: 2,
47
+ start_y: 2,
48
+ commodity: commodity,
49
+ store: authorization.store,
50
+ commodity_status: Commodity::GOOD,
51
+ stack_status: Stack::ALLOCATED
52
+ )
53
+ ReceiptTransaction.create!(
54
+ receipt_authorization: authorization,
55
+ destination: stack,
56
+ quantity: authorization.received_quantity,
57
+ status: Transaction::DRAFT,
58
+ transaction_date: Date.today
59
+ )
60
+ stack
61
+ end
62
+
30
63
  def stack(authorization_id)
31
64
  authorization = ReceiptAuthorization.find(authorization_id)
32
65
  unless authorization.dispatch.dispatch_status == Dispatch::RECEIVED
@@ -0,0 +1,25 @@
1
+ module Cats
2
+ module Core
3
+ class LocationService
4
+ # This method creates FDP from location params, but also creates the
5
+ # related dummy warehouse and store for the FDP
6
+ def create_fdp(code, name, parent_id, description = nil)
7
+ ActiveRecord::Base.transaction do
8
+ fdp = Location.create!(
9
+ code: code, name: name, description: description, location_type: Location::FDP, parent_id: parent_id
10
+ )
11
+ wh_code = "FDP-WH-#{fdp.code}"
12
+ st_code = "FDP-ST-#{fdp.code}"
13
+
14
+ warehouse = Location.create!(
15
+ code: wh_code, name: wh_code, location_type: Location::WAREHOUSE, parent: fdp
16
+ )
17
+ Store.create!(
18
+ code: st_code, name: st_code, length: 200, width: 200, height: 200, warehouse: warehouse
19
+ )
20
+ fdp
21
+ end
22
+ end
23
+ end
24
+ end
25
+ end
data/config/routes.rb CHANGED
@@ -41,6 +41,7 @@ Cats::Core::Engine.routes.draw do
41
41
 
42
42
  get '/regions/:id/woredas', controller: :locations, action: :woredas, as: :region_woredas
43
43
  post '/locations/filter', controller: :locations, action: :filter
44
+ post '/locations/fdp/create', controller: :locations, action: :create_fdp
44
45
  resources :locations, except: %i[destroy] do
45
46
  member do
46
47
  get 'children'
@@ -142,6 +143,18 @@ Cats::Core::Engine.routes.draw do
142
143
  action: :storekeeper_authorizations,
143
144
  as: :storekeeper_receipt_authorizations
144
145
  )
146
+ post(
147
+ '/storekeeper/:id/assign_stores',
148
+ controller: :stores,
149
+ action: :assign_store,
150
+ as: :assign_stores_to_storekeeper
151
+ )
152
+ post(
153
+ '/storekeeper/:id/unassign_stores',
154
+ controller: :stores,
155
+ action: :unassign_store,
156
+ as: :unassign_stores_to_storekeeper
157
+ )
145
158
  post(
146
159
  '/receipt_authorizations/generate',
147
160
  controller: :receipt_authorizations,
@@ -200,6 +213,10 @@ Cats::Core::Engine.routes.draw do
200
213
 
201
214
  get '/warehouses/:id/stores', controller: :stores, action: :index, as: :stores_warehouse
202
215
  get '/hubs/:id/stores', controller: :stores, action: :stores_for_hub, as: :stores_hub
203
- resources :stores, only: %i[index show create update]
216
+ resources :stores, only: %i[index show create update] do
217
+ member do
218
+ get 'fdp'
219
+ end
220
+ end
204
221
  post '/stores/filter', controller: :stores, action: :filter
205
222
  end
@@ -17,10 +17,7 @@ class CreateCatsCoreStores < ActiveRecord::Migration[6.1]
17
17
  null: false,
18
18
  index: { name: 'warehouse_on_stores_indx' },
19
19
  foreign_key: { to_table: :cats_core_locations }
20
- t.references :store_keeper,
21
- null: false,
22
- index: { name: 'store_keeper_on_store_indx' },
23
- foreign_key: { to_table: :cats_core_users }
20
+
24
21
  t.timestamps
25
22
  end
26
23
  end
@@ -1,5 +1,5 @@
1
1
  module Cats
2
2
  module Core
3
- VERSION = '1.4.45'.freeze
3
+ VERSION = '1.4.49'.freeze
4
4
  end
5
5
  end
@@ -2,7 +2,7 @@ FactoryBot.define do
2
2
  factory :dispatch_plan_item, class: 'Cats::Core::DispatchPlanItem' do
3
3
  reference_no { FFaker::Name.name }
4
4
  source factory: :location
5
- destination factory: :location
5
+ destination factory: :woreda
6
6
  dispatch_plan
7
7
  quantity { 100 }
8
8
  unit factory: :unit_of_measure
@@ -19,6 +19,15 @@ FactoryBot.define do
19
19
  factory :fdp, parent: :woreda, class: 'Cats::Core::Location' do
20
20
  location_type { Cats::Core::Location::FDP }
21
21
  parent factory: :woreda
22
+
23
+ trait :with_store do
24
+ after(:create) do |obj|
25
+ wh_code = "FDP-WH-#{obj.code}"
26
+ st_code = "FDP-ST-#{obj.code}"
27
+ warehouse = create(:warehouse, code: wh_code, name: wh_code, parent: obj)
28
+ create(:store, code: st_code, name: st_code, warehouse: warehouse)
29
+ end
30
+ end
22
31
  end
23
32
 
24
33
  factory :hub, parent: :location, class: 'Cats::Core::Location' do
@@ -11,7 +11,5 @@ FactoryBot.define do
11
11
  gangway_width { 4 }
12
12
  gangway_corner_dist { 18 }
13
13
  warehouse
14
- store_keeper factory: :user
15
- store_keeper_id { create(:user).id }
16
14
  end
17
15
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cats_core
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.4.45
4
+ version: 1.4.49
5
5
  platform: ruby
6
6
  authors:
7
7
  - Henock L.
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-06-27 00:00:00.000000000 Z
11
+ date: 2022-06-30 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: active_model_serializers
@@ -122,6 +122,20 @@ dependencies:
122
122
  - - "~>"
123
123
  - !ruby/object:Gem::Version
124
124
  version: 6.0.0
125
+ - !ruby/object:Gem::Dependency
126
+ name: sablon
127
+ requirement: !ruby/object:Gem::Requirement
128
+ requirements:
129
+ - - ">="
130
+ - !ruby/object:Gem::Version
131
+ version: '0'
132
+ type: :runtime
133
+ prerelease: false
134
+ version_requirements: !ruby/object:Gem::Requirement
135
+ requirements:
136
+ - - ">="
137
+ - !ruby/object:Gem::Version
138
+ version: '0'
125
139
  - !ruby/object:Gem::Dependency
126
140
  name: database_cleaner
127
141
  requirement: !ruby/object:Gem::Requirement
@@ -377,6 +391,7 @@ files:
377
391
  - app/services/cats/core/beneficiary_service.rb
378
392
  - app/services/cats/core/dispatch_plan_service.rb
379
393
  - app/services/cats/core/dispatch_service.rb
394
+ - app/services/cats/core/location_service.rb
380
395
  - app/services/cats/core/menu_service.rb
381
396
  - app/services/cats/core/notification_service.rb
382
397
  - app/services/cats/core/round_plan_service.rb