spree_cm_commissioner 2.5.1 → 2.5.2.pre.pre1

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.
Files changed (90) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/test_and_build_gem.yml +2 -2
  3. data/Gemfile.lock +1 -1
  4. data/app/controllers/spree/admin/inventory_items_controller.rb +36 -56
  5. data/app/controllers/spree/admin/stock_managements_controller.rb +14 -3
  6. data/app/controllers/spree/api/v2/storefront/popular_route_places_controller.rb +2 -2
  7. data/app/controllers/spree/api/v2/storefront/transit/draft_orders_controller.rb +4 -4
  8. data/app/controllers/spree/api/v2/tenant/popular_route_places_controller.rb +60 -0
  9. data/app/controllers/spree/api/v2/tenant/routes_controller.rb +50 -0
  10. data/app/controllers/spree/api/v2/tenant/transit/draft_orders_controller.rb +46 -0
  11. data/app/controllers/spree/transit/trips_controller.rb +3 -3
  12. data/app/finders/spree_cm_commissioner/places/find_with_route.rb +12 -12
  13. data/app/finders/spree_cm_commissioner/route_metrics/find_popular.rb +44 -0
  14. data/app/finders/spree_cm_commissioner/routes/find.rb +94 -0
  15. data/app/finders/spree_cm_commissioner/routes/find_popular.rb +19 -35
  16. data/app/interactors/spree_cm_commissioner/stock/permanent_inventory_items_generator.rb +11 -4
  17. data/app/interactors/spree_cm_commissioner/stock/stock_movement_creator.rb +10 -1
  18. data/app/interactors/spree_cm_commissioner/trip_clone_creator.rb +4 -3
  19. data/app/interactors/spree_cm_commissioner/trip_stops_creator.rb +2 -2
  20. data/app/jobs/spree_cm_commissioner/route_metrics/decrease_trip_count_job.rb +10 -0
  21. data/app/jobs/spree_cm_commissioner/route_metrics/increase_fulfilled_order_count_job.rb +10 -0
  22. data/app/jobs/spree_cm_commissioner/route_metrics/increase_order_count_job.rb +10 -0
  23. data/app/jobs/spree_cm_commissioner/route_metrics/increase_trip_count_job.rb +10 -0
  24. data/app/jobs/spree_cm_commissioner/stock/permanent_inventory_items_generator_job.rb +2 -2
  25. data/app/models/concerns/spree_cm_commissioner/route_order_countable.rb +2 -2
  26. data/app/models/spree_cm_commissioner/place.rb +5 -8
  27. data/app/models/spree_cm_commissioner/product_decorator.rb +1 -0
  28. data/app/models/spree_cm_commissioner/route.rb +45 -5
  29. data/app/models/spree_cm_commissioner/route_metric.rb +21 -0
  30. data/app/models/spree_cm_commissioner/route_photo.rb +12 -0
  31. data/app/models/spree_cm_commissioner/trip.rb +8 -33
  32. data/app/models/spree_cm_commissioner/trip_stop.rb +16 -2
  33. data/app/models/spree_cm_commissioner/vendor_decorator.rb +3 -1
  34. data/app/queries/spree_cm_commissioner/trip_query.rb +2 -2
  35. data/app/serializers/spree/v2/tenant/transit_cart_serializer.rb +11 -0
  36. data/app/serializers/spree_cm_commissioner/v2/storefront/route_metric_serializer.rb +13 -0
  37. data/app/serializers/spree_cm_commissioner/v2/storefront/route_serializer.rb +2 -1
  38. data/app/serializers/spree_cm_commissioner/v2/storefront/transit_line_item_serializer.rb +17 -0
  39. data/app/serializers/spree_cm_commissioner/v2/storefront/trip_stop_serializer.rb +1 -1
  40. data/app/services/spree_cm_commissioner/route_metrics/decrease_trip_count.rb +31 -0
  41. data/app/services/spree_cm_commissioner/{routes/increment_fulfilled_order_count.rb → route_metrics/increase_fulfilled_order_count.rb} +3 -3
  42. data/app/services/spree_cm_commissioner/{routes/increment_order_count.rb → route_metrics/increase_order_count.rb} +3 -3
  43. data/app/services/spree_cm_commissioner/route_metrics/increase_trip_count.rb +31 -0
  44. data/app/services/spree_cm_commissioner/{routes/base_update_order_metrics.rb → route_metrics/update_route_metrics.rb} +11 -16
  45. data/app/services/spree_cm_commissioner/routes/create.rb +51 -0
  46. data/app/services/spree_cm_commissioner/routes/update.rb +25 -0
  47. data/app/{interactors/spree_cm_commissioner/transit/draft_order_creator.rb → services/spree_cm_commissioner/transit_order/create.rb} +13 -16
  48. data/app/services/spree_cm_commissioner/trips/create_single_leg.rb +123 -0
  49. data/app/services/spree_cm_commissioner/trips/service_calendars/create_or_update.rb +54 -0
  50. data/app/services/spree_cm_commissioner/trips/update_single_leg.rb +88 -0
  51. data/app/services/spree_cm_commissioner/trips/variants/create.rb +103 -0
  52. data/app/views/spree/admin/inventory_items/prices.html.erb +45 -0
  53. data/app/views/spree/admin/inventory_items/stocks.html.erb +36 -0
  54. data/app/views/spree/admin/stock_managements/calendar.html.erb +105 -12
  55. data/app/views/spree/admin/stock_managements/index.html.erb +9 -8
  56. data/app/views/spree/transit/trip_stops/index.html.erb +4 -2
  57. data/app/views/spree_cm_commissioner/guest_mailer/send_ticket_to_guest.html.erb +0 -1
  58. data/config/initializers/spree_permitted_attributes.rb +11 -0
  59. data/config/routes.rb +12 -7
  60. data/db/migrate/20251224033103_migrate_cm_routes_to_cm_route_metrics.rb +17 -0
  61. data/db/migrate/20251224033910_migrate_cm_vendor_routes_to_cm_routes.rb +30 -0
  62. data/db/migrate/20260105072450_migrate_cm_trip_stops_to_support_trip_connection.rb +12 -0
  63. data/db/migrate/20260108101406_add_allow_booking_to_cm_trips.rb +5 -0
  64. data/lib/spree_cm_commissioner/test_helper/factories/route_factory.rb +7 -6
  65. data/lib/spree_cm_commissioner/test_helper/factories/route_metric_factory.rb +12 -0
  66. data/lib/spree_cm_commissioner/test_helper/factories/route_photo_factory.rb +5 -0
  67. data/lib/spree_cm_commissioner/test_helper/factories/trip_factory.rb +4 -1
  68. data/lib/spree_cm_commissioner/test_helper/factories/trip_stop_factory.rb +3 -1
  69. data/lib/spree_cm_commissioner/test_helper/factories/vendor_factory.rb +2 -0
  70. data/lib/spree_cm_commissioner/test_helper/factories/vendor_place_factory.rb +22 -0
  71. data/lib/spree_cm_commissioner/transit/route_stop.rb +61 -0
  72. data/lib/spree_cm_commissioner/transit/route_stop_collection.rb +175 -0
  73. data/lib/spree_cm_commissioner/transit/trip_form.rb +81 -0
  74. data/lib/spree_cm_commissioner/transit/trip_stop_form.rb +65 -0
  75. data/lib/spree_cm_commissioner/version.rb +1 -1
  76. data/lib/spree_cm_commissioner.rb +4 -0
  77. metadata +42 -21
  78. data/app/jobs/spree_cm_commissioner/transit/route_fulfilled_order_count_incrementer_job.rb +0 -10
  79. data/app/jobs/spree_cm_commissioner/transit/route_order_count_incrementer_job.rb +0 -10
  80. data/app/jobs/spree_cm_commissioner/transit/route_previous_trip_count_decrementer_job.rb +0 -13
  81. data/app/jobs/spree_cm_commissioner/transit/route_trip_count_decrementer_job.rb +0 -10
  82. data/app/jobs/spree_cm_commissioner/transit/route_trip_count_incrementer_job.rb +0 -10
  83. data/app/models/concerns/spree_cm_commissioner/route_trip_count_callbacks.rb +0 -48
  84. data/app/models/spree_cm_commissioner/trip_connection.rb +0 -36
  85. data/app/models/spree_cm_commissioner/vendor_route.rb +0 -9
  86. data/app/services/spree_cm_commissioner/routes/decrement_previous_trip_count.rb +0 -30
  87. data/app/services/spree_cm_commissioner/routes/decrement_trip_count.rb +0 -33
  88. data/app/services/spree_cm_commissioner/routes/increment_trip_count.rb +0 -33
  89. data/app/views/spree/admin/inventory_items/show.html.erb +0 -72
  90. data/lib/spree_cm_commissioner/test_helper/factories/trip_connection_factory.rb +0 -6
@@ -0,0 +1,175 @@
1
+ module SpreeCmCommissioner::Transit
2
+ class RouteStopCollection
3
+ include Enumerable
4
+
5
+ attr_reader :stops
6
+
7
+ def initialize(stops = [])
8
+ @stops = stops
9
+ @errors = []
10
+ end
11
+
12
+ def self.from_hash(array)
13
+ # Handle nil, empty array, or string "[]" when loaded from database
14
+ parsed_array = case array
15
+ when nil
16
+ []
17
+ when String
18
+ JSON.parse(array)
19
+ else
20
+ array
21
+ end
22
+
23
+ stops = Array(parsed_array).each_with_index.map do |raw, index|
24
+ hash = raw.to_h.symbolize_keys
25
+ RouteStop.from_hash(hash.merge(sequence: index))
26
+ end
27
+
28
+ new(stops)
29
+ end
30
+
31
+ def to_h
32
+ @stops.map(&:to_h)
33
+ end
34
+
35
+ def each(&block)
36
+ @stops.each(&block)
37
+ end
38
+
39
+ def [](index)
40
+ @stops[index]
41
+ end
42
+
43
+ def first
44
+ @stops.first
45
+ end
46
+
47
+ def last
48
+ @stops.last
49
+ end
50
+
51
+ def length
52
+ @stops.length
53
+ end
54
+
55
+ def empty?
56
+ @stops.empty?
57
+ end
58
+
59
+ def multi_leg?
60
+ branch_location_ids = @stops.select(&:branch?).map(&:location_id).uniq
61
+ branch_location_ids.length >= 3
62
+ end
63
+
64
+ def by_location
65
+ @stops.group_by(&:location_id)
66
+ end
67
+
68
+ # Fetches vendor places and groups route stops by their location object
69
+ # Returns: { location_obj => [route_stop_a, route_stop_b], location_obj_2 => [...] }
70
+ # Example: If you have stops for branches in "Bangkok" and "Chiang Mai",
71
+ # this returns all stops grouped by their location object
72
+ def by_location_with_data
73
+ return {} if @stops.empty?
74
+
75
+ # Extract unique vendor_place_ids from all stops
76
+ vendor_place_ids = @stops.map(&:vendor_place_id).compact.uniq
77
+ return {} if vendor_place_ids.empty?
78
+
79
+ # Single query: fetch all vendor places with their locations
80
+ # index_by(:id) creates a hash for O(1) lookup: { vendor_place_id => vendor_place_obj }
81
+ vendor_places = SpreeCmCommissioner::VendorPlace.where(id: vendor_place_ids).includes(:location).index_by(&:id)
82
+
83
+ grouped = {}
84
+ @stops.each do |stop|
85
+ # Set the vendor_place object on the stop for later use
86
+ stop.vendor_place = vendor_places[stop.vendor_place_id]
87
+
88
+ # Get the location from the vendor_place (e.g., "Bangkok" location)
89
+ location = stop.vendor_place&.location
90
+ next if location.nil?
91
+
92
+ # Group stops by location object
93
+ grouped[location] ||= []
94
+ grouped[location] << stop
95
+ end
96
+
97
+ grouped
98
+ end
99
+
100
+ # Groups route stops by their location in sequence order
101
+ # Returns an array of hashes where each hash contains:
102
+ # - location: the VendorPlace representing the location
103
+ # - stops: array of route stops at that location, sorted by sequence
104
+ # Example usage: @stops.group_by_sequence
105
+ # {
106
+ # location_object_1 => [stop1, stop2, stop3],
107
+ # location_object_2 => [stop4, stop5]
108
+ # }
109
+ # Stop 0: Location A
110
+ # Stop 1: Location A
111
+ # Stop 2: Location B
112
+ # Stop 3: Location A ← Same location again (For case when the bus has the same origin/destination)
113
+ def group_by_sequence
114
+ return [] if @stops.blank?
115
+
116
+ by_location = by_location_with_data || {}
117
+
118
+ # location_id => location_vendor_place (the "location" vendor_place in the hash key)
119
+ location_by_id = by_location.keys.index_by(&:id)
120
+
121
+ ordered_stops =
122
+ by_location.values
123
+ .flatten
124
+ .compact
125
+ .sort_by { |s| s.sequence.to_i }
126
+
127
+ grouped_stops = []
128
+ current_location_id = nil
129
+ current_group = nil
130
+
131
+ ordered_stops.each do |stop|
132
+ stop_location_id = stop.location_id
133
+
134
+ if stop_location_id != current_location_id
135
+ current_location_id = stop_location_id
136
+ current_group = {
137
+ location: location_by_id[stop_location_id],
138
+ stops: []
139
+ }
140
+ grouped_stops << current_group
141
+ end
142
+
143
+ current_group[:stops] << stop
144
+ end
145
+
146
+ grouped_stops
147
+ end
148
+
149
+ def valid?
150
+ errors.empty?
151
+ end
152
+
153
+ def errors
154
+ @errors = []
155
+
156
+ # Check each stop is valid
157
+ @stops.each_with_index do |stop, index|
158
+ next if stop.valid?
159
+
160
+ stop.errors.each do |error|
161
+ @errors << "Stop #{index}: #{error}"
162
+ end
163
+ end
164
+
165
+ # Check for duplicate vendor_place_ids
166
+ vendor_place_ids = @stops.map(&:vendor_place_id)
167
+ duplicates = vendor_place_ids.tally.select { |_, count| count > 1 }.keys
168
+ duplicates.each do |dup_id|
169
+ @errors << "vendor_place_id #{dup_id} appears more than once"
170
+ end
171
+
172
+ @errors
173
+ end
174
+ end
175
+ end
@@ -0,0 +1,81 @@
1
+ module SpreeCmCommissioner::Transit
2
+ class TripForm
3
+ include ActiveModel::Model
4
+
5
+ attr_accessor :route_id,
6
+ :name,
7
+ :short_name,
8
+ :price,
9
+ :allow_booking,
10
+ :allow_seat_selection,
11
+ :route_type,
12
+ :trip_stops, # TripStopForm[]
13
+ :service_calendar # monday, tuesday, wednesday, thursday, friday, saturday, sunday, start_date, end_date
14
+
15
+ def multi_leg?
16
+ trip_stops.map(&:location_id).uniq.size > 2
17
+ end
18
+
19
+ def total_duration_seconds
20
+ return 0 if trip_stops.size < 2
21
+
22
+ minutes = trip_stops[0...-1].sum { |s| s.duration_in_minutes || 0 }
23
+ minutes * 60
24
+ end
25
+
26
+ def valid_data? # rubocop:disable Metrics/CyclomaticComplexity,Metrics/PerceivedComplexity
27
+ errors.clear
28
+
29
+ errors.add(:route_id, 'must be present') if route_id.blank?
30
+ errors.add(:trip_stops, 'must be present') if trip_stops.blank? || trip_stops.size < 2
31
+
32
+ first_stop = trip_stops&.first
33
+ last_stop = trip_stops&.last
34
+
35
+ errors.add(:trip_stops, 'first stop must allow boarding') unless first_stop&.allow_boarding?
36
+ errors.add(:trip_stops, 'last stop must allow drop off') unless last_stop&.allow_drop_off?
37
+ errors.add(:departure_time, 'missing on first stop') if first_stop&.departure_time.blank?
38
+
39
+ errors.empty?
40
+ end
41
+
42
+ # Groups trip_stops into legs by location changes
43
+ # Separates legs when location_id changes (at branch stops)
44
+ # Break stops (stop_type = :stop) are included but don't trigger separation
45
+ #
46
+ # Example:
47
+ # [PP1, PP2, PTT1(break stop), BTB1, BTB2, PPT2(break stop), POIPET1, POIPET1]
48
+ #
49
+ # Output (legs):
50
+ # [
51
+ # [PP1, PP2, PTT, BTB1, BTB2],
52
+ # [BTB1, BTB2, PPT1, POIPET1, POIPET1]
53
+ # ]
54
+ def trip_stops_grouped_by_leg(stops)
55
+ return [] if trip_stops.empty?
56
+
57
+ legs = []
58
+ current_leg = []
59
+ last_location_id = nil
60
+
61
+ trip_stops.each do |trip_stop|
62
+ stop = stops[trip_stop.stop_id]
63
+
64
+ # If location changed and we have stops in current leg, start a new leg
65
+ current_leg << trip_stop
66
+ if last_location_id.present? && last_location_id != trip_stop.location_id && current_leg.any?
67
+ # Include the first stop of new location in previous leg
68
+ legs << current_leg
69
+ current_leg = [trip_stop]
70
+ end
71
+
72
+ # Update location only for branch stops (not for "just stops")
73
+ last_location_id = trip_stop.location_id if stop.branch?
74
+ end
75
+
76
+ # Add final leg if it has stops
77
+ legs << current_leg if current_leg.any?
78
+ legs
79
+ end
80
+ end
81
+ end
@@ -0,0 +1,65 @@
1
+ module SpreeCmCommissioner::Transit
2
+ class TripStopForm
3
+ attr_accessor :location_id,
4
+ :stop_id,
5
+ :departure_time,
6
+ :duration_in_hours,
7
+ :route_type,
8
+ #
9
+ # when create, vehicle_type_id is required. But if board_to_trip_id present (from another route), we can copy from that trip.
10
+ # when edit, vehicle_type_id can be changed since we already copied the seat layout.
11
+ :vehicle_type_id,
12
+ #
13
+ # (optional), same as vehicle_type_id.
14
+ :vehicle_id,
15
+ #
16
+ # when create:
17
+ # if board_to_trip_id present, it mean it link to another trip to board.
18
+ #
19
+ # when edit:
20
+ # board_to_trip_id can't be set to nil or changed to another trip id.
21
+ :board_to_trip_id,
22
+ #
23
+ # for first stop, allow_boarding must be true.
24
+ # for last stop, allow_boarding must be false.
25
+ # for middle stops, both can be true/false.
26
+ #
27
+ # but when stop.type is not branch (eg. stop), allow_boarding must be false.
28
+ :allow_boarding,
29
+ #
30
+ # for first stop, allow_drop_off must be false.
31
+ # for last stop, allow_drop_off must be true.
32
+ # for middle stops, both can be true/false.
33
+ #
34
+ # but when stop.type is not branch (eg. stop), allow_drop_off must be false.
35
+ :allow_drop_off,
36
+ #
37
+ # when stop.type is branch, admin can toggle allow_seat_selection.
38
+ # but for edit, if board_to_trip_id is from another route, allow_seat_selection can't be changed.
39
+ # only allow changed from its own route.
40
+ :allow_seat_selection,
41
+ #
42
+ # when create, allow_booking only when stop.type is branch, use it to assign to create sub-trip.
43
+ # but for edit, if board_to_trip_id is from another route, allow_booking can't be changed.
44
+ # only allow changed from its own route.
45
+ :allow_booking,
46
+ :sequence,
47
+ #
48
+ # set from create service
49
+ :vendor_id
50
+
51
+ def allow_boarding?
52
+ ActiveModel::Type::Boolean.new.cast(allow_boarding)
53
+ end
54
+
55
+ def allow_drop_off?
56
+ ActiveModel::Type::Boolean.new.cast(allow_drop_off)
57
+ end
58
+
59
+ def duration_in_minutes
60
+ return nil if duration_in_hours.blank?
61
+
62
+ (duration_in_hours.to_f * 60).to_i
63
+ end
64
+ end
65
+ end
@@ -1,5 +1,5 @@
1
1
  module SpreeCmCommissioner
2
- VERSION = '2.5.1'.freeze
2
+ VERSION = '2.5.2-pre1'.freeze
3
3
 
4
4
  module_function
5
5
 
@@ -23,6 +23,10 @@ require 'spree_cm_commissioner/trip_query_result'
23
23
  require 'spree_cm_commissioner/cached_inventory_item'
24
24
  require 'spree_cm_commissioner/transit/leg'
25
25
  require 'spree_cm_commissioner/transit/seat_selection'
26
+ require 'spree_cm_commissioner/transit/route_stop'
27
+ require 'spree_cm_commissioner/transit/route_stop_collection'
28
+ require 'spree_cm_commissioner/transit/trip_form'
29
+ require 'spree_cm_commissioner/transit/trip_stop_form'
26
30
  require 'spree_cm_commissioner/intercity_taxi/map_place'
27
31
  require 'spree_cm_commissioner/distance'
28
32
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: spree_cm_commissioner
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.5.1
4
+ version: 2.5.2.pre.pre1
5
5
  platform: ruby
6
6
  authors:
7
7
  - You
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2026-01-27 00:00:00.000000000 Z
11
+ date: 2026-01-28 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: spree
@@ -1033,13 +1033,16 @@ files:
1033
1033
  - app/controllers/spree/api/v2/tenant/order_histories_controller.rb
1034
1034
  - app/controllers/spree/api/v2/tenant/pin_code_checkers_controller.rb
1035
1035
  - app/controllers/spree/api/v2/tenant/pin_code_generators_controller.rb
1036
+ - app/controllers/spree/api/v2/tenant/popular_route_places_controller.rb
1036
1037
  - app/controllers/spree/api/v2/tenant/product_dynamic_fields_controller.rb
1037
1038
  - app/controllers/spree/api/v2/tenant/products_controller.rb
1038
1039
  - app/controllers/spree/api/v2/tenant/profile_images_controller.rb
1039
1040
  - app/controllers/spree/api/v2/tenant/reset_passwords_controller.rb
1041
+ - app/controllers/spree/api/v2/tenant/routes_controller.rb
1040
1042
  - app/controllers/spree/api/v2/tenant/s3_signed_urls_controller.rb
1041
1043
  - app/controllers/spree/api/v2/tenant/taxons_controller.rb
1042
1044
  - app/controllers/spree/api/v2/tenant/tickets_controller.rb
1045
+ - app/controllers/spree/api/v2/tenant/transit/draft_orders_controller.rb
1043
1046
  - app/controllers/spree/api/v2/tenant/trip_places_controller.rb
1044
1047
  - app/controllers/spree/api/v2/tenant/trip_search_controller.rb
1045
1048
  - app/controllers/spree/api/v2/tenant/trips_controller.rb
@@ -1147,6 +1150,8 @@ files:
1147
1150
  - app/finders/spree_cm_commissioner/payment_methods/group_by_bank.rb
1148
1151
  - app/finders/spree_cm_commissioner/places/find_with_route.rb
1149
1152
  - app/finders/spree_cm_commissioner/products/find_decorator.rb
1153
+ - app/finders/spree_cm_commissioner/route_metrics/find_popular.rb
1154
+ - app/finders/spree_cm_commissioner/routes/find.rb
1150
1155
  - app/finders/spree_cm_commissioner/routes/find_popular.rb
1151
1156
  - app/helpers/spree/admin/base_helper_decorator.rb
1152
1157
  - app/helpers/spree/admin/google_wallets_helper.rb
@@ -1273,7 +1278,6 @@ files:
1273
1278
  - app/interactors/spree_cm_commissioner/telegram_web_app_vendor_user_authorizer.rb
1274
1279
  - app/interactors/spree_cm_commissioner/telegram_web_app_vendor_user_checker.rb
1275
1280
  - app/interactors/spree_cm_commissioner/transactional_email_sender.rb
1276
- - app/interactors/spree_cm_commissioner/transit/draft_order_creator.rb
1277
1281
  - app/interactors/spree_cm_commissioner/trip_clone_creator.rb
1278
1282
  - app/interactors/spree_cm_commissioner/trip_stops_creator.rb
1279
1283
  - app/interactors/spree_cm_commissioner/unique_device_token_cron_executor.rb
@@ -1342,6 +1346,10 @@ files:
1342
1346
  - app/jobs/spree_cm_commissioner/product_event_id_to_children_syncer_job.rb
1343
1347
  - app/jobs/spree_cm_commissioner/queue_order_webhooks_requests_job.rb
1344
1348
  - app/jobs/spree_cm_commissioner/reports_assigner_job.rb
1349
+ - app/jobs/spree_cm_commissioner/route_metrics/decrease_trip_count_job.rb
1350
+ - app/jobs/spree_cm_commissioner/route_metrics/increase_fulfilled_order_count_job.rb
1351
+ - app/jobs/spree_cm_commissioner/route_metrics/increase_order_count_job.rb
1352
+ - app/jobs/spree_cm_commissioner/route_metrics/increase_trip_count_job.rb
1345
1353
  - app/jobs/spree_cm_commissioner/seats/bulk_release_on_hold_blocks_job.rb
1346
1354
  - app/jobs/spree_cm_commissioner/seats/release_expired_blocks_job.rb
1347
1355
  - app/jobs/spree_cm_commissioner/sms_job.rb
@@ -1355,11 +1363,6 @@ files:
1355
1363
  - app/jobs/spree_cm_commissioner/telegram_debug_pin_code_sender_job.rb
1356
1364
  - app/jobs/spree_cm_commissioner/telegram_notification_sender_job.rb
1357
1365
  - app/jobs/spree_cm_commissioner/telegram_start_message_sender_job.rb
1358
- - app/jobs/spree_cm_commissioner/transit/route_fulfilled_order_count_incrementer_job.rb
1359
- - app/jobs/spree_cm_commissioner/transit/route_order_count_incrementer_job.rb
1360
- - app/jobs/spree_cm_commissioner/transit/route_previous_trip_count_decrementer_job.rb
1361
- - app/jobs/spree_cm_commissioner/transit/route_trip_count_decrementer_job.rb
1362
- - app/jobs/spree_cm_commissioner/transit/route_trip_count_incrementer_job.rb
1363
1366
  - app/jobs/spree_cm_commissioner/unique_device_token_cron_job.rb
1364
1367
  - app/jobs/spree_cm_commissioner/variants_public_metadata_updater_job.rb
1365
1368
  - app/jobs/spree_cm_commissioner/vendor_creation_telegram_alert_sender_job.rb
@@ -1400,7 +1403,6 @@ files:
1400
1403
  - app/models/concerns/spree_cm_commissioner/product_delegation.rb
1401
1404
  - app/models/concerns/spree_cm_commissioner/product_type.rb
1402
1405
  - app/models/concerns/spree_cm_commissioner/route_order_countable.rb
1403
- - app/models/concerns/spree_cm_commissioner/route_trip_count_callbacks.rb
1404
1406
  - app/models/concerns/spree_cm_commissioner/route_type.rb
1405
1407
  - app/models/concerns/spree_cm_commissioner/service_calendar_type.rb
1406
1408
  - app/models/concerns/spree_cm_commissioner/service_recommendations.rb
@@ -1563,6 +1565,8 @@ files:
1563
1565
  - app/models/spree_cm_commissioner/role_decorator.rb
1564
1566
  - app/models/spree_cm_commissioner/role_permission.rb
1565
1567
  - app/models/spree_cm_commissioner/route.rb
1568
+ - app/models/spree_cm_commissioner/route_metric.rb
1569
+ - app/models/spree_cm_commissioner/route_photo.rb
1566
1570
  - app/models/spree_cm_commissioner/s3_presigned_url.rb
1567
1571
  - app/models/spree_cm_commissioner/s3_presigned_url_builder.rb
1568
1572
  - app/models/spree_cm_commissioner/saved_guest.rb
@@ -1601,7 +1605,6 @@ files:
1601
1605
  - app/models/spree_cm_commissioner/tenant.rb
1602
1606
  - app/models/spree_cm_commissioner/transactional_email.rb
1603
1607
  - app/models/spree_cm_commissioner/trip.rb
1604
- - app/models/spree_cm_commissioner/trip_connection.rb
1605
1608
  - app/models/spree_cm_commissioner/trip_stop.rb
1606
1609
  - app/models/spree_cm_commissioner/user_decorator.rb
1607
1610
  - app/models/spree_cm_commissioner/user_deletion_survey.rb
@@ -1627,7 +1630,6 @@ files:
1627
1630
  - app/models/spree_cm_commissioner/vendor_photo.rb
1628
1631
  - app/models/spree_cm_commissioner/vendor_place.rb
1629
1632
  - app/models/spree_cm_commissioner/vendor_promotion_rule.rb
1630
- - app/models/spree_cm_commissioner/vendor_route.rb
1631
1633
  - app/models/spree_cm_commissioner/vendor_web_promotion_banner.rb
1632
1634
  - app/models/spree_cm_commissioner/video.rb
1633
1635
  - app/models/spree_cm_commissioner/video_on_demand.rb
@@ -1893,6 +1895,7 @@ files:
1893
1895
  - app/serializers/spree/v2/tenant/taxon_serializer.rb
1894
1896
  - app/serializers/spree/v2/tenant/taxonomy_serializer.rb
1895
1897
  - app/serializers/spree/v2/tenant/ticket_serializer.rb
1898
+ - app/serializers/spree/v2/tenant/transit_cart_serializer.rb
1896
1899
  - app/serializers/spree/v2/tenant/trip_place_serializer.rb
1897
1900
  - app/serializers/spree/v2/tenant/trip_query_result_serializer.rb
1898
1901
  - app/serializers/spree/v2/tenant/trip_serializer.rb
@@ -1964,6 +1967,7 @@ files:
1964
1967
  - app/serializers/spree_cm_commissioner/v2/storefront/qr_url_serializer.rb
1965
1968
  - app/serializers/spree_cm_commissioner/v2/storefront/reserved_block_serializer.rb
1966
1969
  - app/serializers/spree_cm_commissioner/v2/storefront/reset_password_serializer.rb
1970
+ - app/serializers/spree_cm_commissioner/v2/storefront/route_metric_serializer.rb
1967
1971
  - app/serializers/spree_cm_commissioner/v2/storefront/route_serializer.rb
1968
1972
  - app/serializers/spree_cm_commissioner/v2/storefront/saved_guest_serializer.rb
1969
1973
  - app/serializers/spree_cm_commissioner/v2/storefront/seat_layout_serializer.rb
@@ -1971,6 +1975,7 @@ files:
1971
1975
  - app/serializers/spree_cm_commissioner/v2/storefront/self_check_in_serializer.rb
1972
1976
  - app/serializers/spree_cm_commissioner/v2/storefront/stock_item_serializer.rb
1973
1977
  - app/serializers/spree_cm_commissioner/v2/storefront/taxon_include_product_serializer.rb
1978
+ - app/serializers/spree_cm_commissioner/v2/storefront/transit_line_item_serializer.rb
1974
1979
  - app/serializers/spree_cm_commissioner/v2/storefront/trip_place_serializer.rb
1975
1980
  - app/serializers/spree_cm_commissioner/v2/storefront/trip_query_result_serializer.rb
1976
1981
  - app/serializers/spree_cm_commissioner/v2/storefront/trip_result_serializer.rb
@@ -2065,12 +2070,13 @@ files:
2065
2070
  - app/services/spree_cm_commissioner/pricing_rules/update.rb
2066
2071
  - app/services/spree_cm_commissioner/role_permissions_constructor.rb
2067
2072
  - app/services/spree_cm_commissioner/role_permissions_loader.rb
2068
- - app/services/spree_cm_commissioner/routes/base_update_order_metrics.rb
2069
- - app/services/spree_cm_commissioner/routes/decrement_previous_trip_count.rb
2070
- - app/services/spree_cm_commissioner/routes/decrement_trip_count.rb
2071
- - app/services/spree_cm_commissioner/routes/increment_fulfilled_order_count.rb
2072
- - app/services/spree_cm_commissioner/routes/increment_order_count.rb
2073
- - app/services/spree_cm_commissioner/routes/increment_trip_count.rb
2073
+ - app/services/spree_cm_commissioner/route_metrics/decrease_trip_count.rb
2074
+ - app/services/spree_cm_commissioner/route_metrics/increase_fulfilled_order_count.rb
2075
+ - app/services/spree_cm_commissioner/route_metrics/increase_order_count.rb
2076
+ - app/services/spree_cm_commissioner/route_metrics/increase_trip_count.rb
2077
+ - app/services/spree_cm_commissioner/route_metrics/update_route_metrics.rb
2078
+ - app/services/spree_cm_commissioner/routes/create.rb
2079
+ - app/services/spree_cm_commissioner/routes/update.rb
2074
2080
  - app/services/spree_cm_commissioner/rsa_service.rb
2075
2081
  - app/services/spree_cm_commissioner/seats/bulk_release_on_hold_blocks.rb
2076
2082
  - app/services/spree_cm_commissioner/seats/release_expired_blocks.rb
@@ -2081,7 +2087,12 @@ files:
2081
2087
  - app/services/spree_cm_commissioner/telegram_alerts/integration_sync_failure.rb
2082
2088
  - app/services/spree_cm_commissioner/transit/export_order.rb
2083
2089
  - app/services/spree_cm_commissioner/transit/legs_builder_service.rb
2090
+ - app/services/spree_cm_commissioner/transit_order/create.rb
2091
+ - app/services/spree_cm_commissioner/trips/create_single_leg.rb
2084
2092
  - app/services/spree_cm_commissioner/trips/search.rb
2093
+ - app/services/spree_cm_commissioner/trips/service_calendars/create_or_update.rb
2094
+ - app/services/spree_cm_commissioner/trips/update_single_leg.rb
2095
+ - app/services/spree_cm_commissioner/trips/variants/create.rb
2085
2096
  - app/services/spree_cm_commissioner/update_guest_service.rb
2086
2097
  - app/services/spree_cm_commissioner/user_authenticator.rb
2087
2098
  - app/services/spree_cm_commissioner/user_roles_assigner.rb
@@ -2196,7 +2207,8 @@ files:
2196
2207
  - app/views/spree/admin/integrations/edit.html.erb
2197
2208
  - app/views/spree/admin/integrations/index.html.erb
2198
2209
  - app/views/spree/admin/integrations/new.html.erb
2199
- - app/views/spree/admin/inventory_items/show.html.erb
2210
+ - app/views/spree/admin/inventory_items/prices.html.erb
2211
+ - app/views/spree/admin/inventory_items/stocks.html.erb
2200
2212
  - app/views/spree/admin/kyc/_form.html.erb
2201
2213
  - app/views/spree/admin/kyc/edit.html.erb
2202
2214
  - app/views/spree/admin/line_items/_form.html.erb
@@ -2998,10 +3010,14 @@ files:
2998
3010
  - db/migrate/20251127074809_change_guest_dynamic_fields_value_from_jsonb_to_text.rb
2999
3011
  - db/migrate/20251209022924_add_contact_fields_to_cm_tenants.rb
3000
3012
  - db/migrate/20251219035243_add_migrations_to_support_vehicle_types.rb
3013
+ - db/migrate/20251224033103_migrate_cm_routes_to_cm_route_metrics.rb
3014
+ - db/migrate/20251224033910_migrate_cm_vendor_routes_to_cm_routes.rb
3001
3015
  - db/migrate/20251225100000_add_age_group_to_cm_guests.rb
3002
3016
  - db/migrate/20260105024742_add_type_to_cm_pricing_actions.rb
3003
3017
  - db/migrate/20260105072146_add_nationality_group_and_age_group_to_cm_saved_guests.rb
3018
+ - db/migrate/20260105072450_migrate_cm_trip_stops_to_support_trip_connection.rb
3004
3019
  - db/migrate/20260106093359_add_contact_phone_to_cm_vendor_places.rb
3020
+ - db/migrate/20260108101406_add_allow_booking_to_cm_trips.rb
3005
3021
  - db/migrate/20260121024645_add_nationality_group_to_cm_guests.rb
3006
3022
  - db/migrate/20260126110528_seed_user_initial_usernames.rb
3007
3023
  - docker-compose.yml
@@ -3097,6 +3113,8 @@ files:
3097
3113
  - lib/spree_cm_commissioner/test_helper/factories/role.rb
3098
3114
  - lib/spree_cm_commissioner/test_helper/factories/role_permission_factory.rb
3099
3115
  - lib/spree_cm_commissioner/test_helper/factories/route_factory.rb
3116
+ - lib/spree_cm_commissioner/test_helper/factories/route_metric_factory.rb
3117
+ - lib/spree_cm_commissioner/test_helper/factories/route_photo_factory.rb
3100
3118
  - lib/spree_cm_commissioner/test_helper/factories/saved_guest_factory.rb
3101
3119
  - lib/spree_cm_commissioner/test_helper/factories/seat_layout_factory.rb
3102
3120
  - lib/spree_cm_commissioner/test_helper/factories/seat_section_factory.rb
@@ -3113,7 +3131,6 @@ files:
3113
3131
  - lib/spree_cm_commissioner/test_helper/factories/telegram_bot_factory.rb
3114
3132
  - lib/spree_cm_commissioner/test_helper/factories/tenant_factory.rb
3115
3133
  - lib/spree_cm_commissioner/test_helper/factories/transactional_email_factory.rb
3116
- - lib/spree_cm_commissioner/test_helper/factories/trip_connection_factory.rb
3117
3134
  - lib/spree_cm_commissioner/test_helper/factories/trip_factory.rb
3118
3135
  - lib/spree_cm_commissioner/test_helper/factories/trip_stop_factory.rb
3119
3136
  - lib/spree_cm_commissioner/test_helper/factories/user_deletion_reasons_factory.rb
@@ -3131,7 +3148,11 @@ files:
3131
3148
  - lib/spree_cm_commissioner/test_helper/factories/webhook_subscriber_factory.rb
3132
3149
  - lib/spree_cm_commissioner/test_helper/factories/webhook_subscriber_rule_factory.rb
3133
3150
  - lib/spree_cm_commissioner/transit/leg.rb
3151
+ - lib/spree_cm_commissioner/transit/route_stop.rb
3152
+ - lib/spree_cm_commissioner/transit/route_stop_collection.rb
3134
3153
  - lib/spree_cm_commissioner/transit/seat_selection.rb
3154
+ - lib/spree_cm_commissioner/transit/trip_form.rb
3155
+ - lib/spree_cm_commissioner/transit/trip_stop_form.rb
3135
3156
  - lib/spree_cm_commissioner/trip_query_result.rb
3136
3157
  - lib/spree_cm_commissioner/trip_result.rb
3137
3158
  - lib/spree_cm_commissioner/user_session_jwt_token.rb
@@ -3180,9 +3201,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
3180
3201
  version: '2.7'
3181
3202
  required_rubygems_version: !ruby/object:Gem::Requirement
3182
3203
  requirements:
3183
- - - ">="
3204
+ - - ">"
3184
3205
  - !ruby/object:Gem::Version
3185
- version: '0'
3206
+ version: 1.3.1
3186
3207
  requirements:
3187
3208
  - none
3188
3209
  rubygems_version: 3.4.1
@@ -1,10 +0,0 @@
1
- module SpreeCmCommissioner
2
- module Transit
3
- class RouteFulfilledOrderCountIncrementerJob < ApplicationUniqueJob
4
- def perform(options = {})
5
- order = Spree::Order.find(options[:order_id])
6
- SpreeCmCommissioner::Routes::IncrementFulfilledOrderCount.call(order: order)
7
- end
8
- end
9
- end
10
- end
@@ -1,10 +0,0 @@
1
- module SpreeCmCommissioner
2
- module Transit
3
- class RouteOrderCountIncrementerJob < ApplicationUniqueJob
4
- def perform(options = {})
5
- order = Spree::Order.find(options[:order_id])
6
- SpreeCmCommissioner::Routes::IncrementOrderCount.call(order: order)
7
- end
8
- end
9
- end
10
- end
@@ -1,13 +0,0 @@
1
- # Perform the previous-route decrement outside the Trip transaction.
2
-
3
- module SpreeCmCommissioner
4
- module Transit
5
- class RoutePreviousTripCountDecrementerJob < ApplicationUniqueJob
6
- queue_as :default
7
-
8
- def perform(options = {})
9
- SpreeCmCommissioner::Routes::DecrementPreviousTripCount.call(previous_route_id: options[:previous_route_id])
10
- end
11
- end
12
- end
13
- end
@@ -1,10 +0,0 @@
1
- module SpreeCmCommissioner
2
- module Transit
3
- class RouteTripCountDecrementerJob < ApplicationUniqueJob
4
- def perform(options = {})
5
- trip = SpreeCmCommissioner::Trip.find(options[:trip_id])
6
- SpreeCmCommissioner::Routes::DecrementTripCount.call(trip: trip)
7
- end
8
- end
9
- end
10
- end
@@ -1,10 +0,0 @@
1
- module SpreeCmCommissioner
2
- module Transit
3
- class RouteTripCountIncrementerJob < ApplicationUniqueJob
4
- def perform(options = {})
5
- trip = SpreeCmCommissioner::Trip.find(options[:trip_id])
6
- SpreeCmCommissioner::Routes::IncrementTripCount.call(trip: trip)
7
- end
8
- end
9
- end
10
- end