workarea-global_e 1.2.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (232) hide show
  1. checksums.yaml +7 -0
  2. data/.eslintrc.json +37 -0
  3. data/.github/ISSUE_TEMPLATE/bug_report.md +37 -0
  4. data/.github/ISSUE_TEMPLATE/documentation-request.md +17 -0
  5. data/.github/ISSUE_TEMPLATE/feature_request.md +20 -0
  6. data/.github/workflows/ci.yml +77 -0
  7. data/.gitignore +20 -0
  8. data/.rubocop.yml +2 -0
  9. data/.ruby-version +1 -0
  10. data/CHANGELOG.md +261 -0
  11. data/Gemfile +16 -0
  12. data/README.md +39 -0
  13. data/Rakefile +59 -0
  14. data/app/assets/javascripts/workarea/storefront/global_e/modules/checkout_info_validator.js +122 -0
  15. data/app/assets/javascripts/workarea/storefront/global_e/modules/suppress_price_ranges.js +19 -0
  16. data/app/controllers/workarea/admin/country_exceptions_controller.rb +67 -0
  17. data/app/controllers/workarea/admin/fixed_prices_controller.rb +89 -0
  18. data/app/controllers/workarea/admin/orders_controller.decorator +6 -0
  19. data/app/controllers/workarea/storefront/application_controller.decorator +30 -0
  20. data/app/controllers/workarea/storefront/checkouts_controller.decorator +22 -0
  21. data/app/controllers/workarea/storefront/ge_checkouts_controller.rb +10 -0
  22. data/app/controllers/workarea/storefront/global_e_controller.rb +42 -0
  23. data/app/controllers/workarea/storefront/globale/api_controller.rb +108 -0
  24. data/app/controllers/workarea/storefront/globale/refund_controller.rb +65 -0
  25. data/app/controllers/workarea/storefront/users/logins_controller.decorator +13 -0
  26. data/app/helpers/workarea/admin/global_e_helpers.rb +28 -0
  27. data/app/models/workarea/address.decorator +11 -0
  28. data/app/models/workarea/catalog/product.decorator +14 -0
  29. data/app/models/workarea/fulfillment/status/partially_refunded.rb +13 -0
  30. data/app/models/workarea/fulfillment/status/refunded.rb +15 -0
  31. data/app/models/workarea/fulfillment.decorator +55 -0
  32. data/app/models/workarea/global_e/country_exception.rb +37 -0
  33. data/app/models/workarea/global_e/fixed_price.rb +93 -0
  34. data/app/models/workarea/global_e/order_api_events.rb +29 -0
  35. data/app/models/workarea/order/item.decorator +46 -0
  36. data/app/models/workarea/order/status/pending_global_e_fraud_check.rb +12 -0
  37. data/app/models/workarea/order.decorator +64 -0
  38. data/app/models/workarea/payment/status/global_e_appoved.rb +9 -0
  39. data/app/models/workarea/payment/status/pending_global_e_fraud_check.rb +9 -0
  40. data/app/models/workarea/payment/tender/global_e_payment.rb +16 -0
  41. data/app/models/workarea/payment.decorator +10 -0
  42. data/app/models/workarea/price_adjustment.decorator +13 -0
  43. data/app/models/workarea/price_adjustment_set.decorator +25 -0
  44. data/app/models/workarea/pricing/calculators/item_calculator.decorator +48 -0
  45. data/app/models/workarea/pricing/collection.decorator +90 -0
  46. data/app/models/workarea/pricing/discount/appliation_group.decorator +16 -0
  47. data/app/models/workarea/pricing/discount/international_item_proxy.rb +27 -0
  48. data/app/models/workarea/pricing/discount/international_order.rb +29 -0
  49. data/app/models/workarea/pricing/discount.decorator +65 -0
  50. data/app/models/workarea/pricing/price_distributor.decorator +37 -0
  51. data/app/models/workarea/pricing/request.decorator +17 -0
  52. data/app/models/workarea/pricing/sku.decorator +17 -0
  53. data/app/models/workarea/search/admin/order.decorator +11 -0
  54. data/app/models/workarea/shipping/sku.decorator +23 -0
  55. data/app/models/workarea/shipping.decorator +11 -0
  56. data/app/models/workarea/user.decorator +10 -0
  57. data/app/seeds/workarea/global_e_seeds.rb +66 -0
  58. data/app/services/workarea/create_fulfillment.decorator +12 -0
  59. data/app/services/workarea/global_e/address_details.rb +218 -0
  60. data/app/services/workarea/global_e/api/notify_order_refunded.rb +45 -0
  61. data/app/services/workarea/global_e/api/perform_order_payment.rb +46 -0
  62. data/app/services/workarea/global_e/api/remove_restricted_products.rb +28 -0
  63. data/app/services/workarea/global_e/api/send_order_to_merchant/item_pricer.rb +147 -0
  64. data/app/services/workarea/global_e/api/send_order_to_merchant/save_user.rb +59 -0
  65. data/app/services/workarea/global_e/api/send_order_to_merchant.rb +359 -0
  66. data/app/services/workarea/global_e/api/update_order_shipping_info.rb +38 -0
  67. data/app/services/workarea/global_e/api/update_order_status/canceled.rb +42 -0
  68. data/app/services/workarea/global_e/api/update_order_status.rb +28 -0
  69. data/app/services/workarea/global_e/attribute.rb +44 -0
  70. data/app/services/workarea/global_e/brand.rb +19 -0
  71. data/app/services/workarea/global_e/cart_user_details.rb +34 -0
  72. data/app/services/workarea/global_e/category.rb +19 -0
  73. data/app/services/workarea/global_e/checkout_cart_info.rb +358 -0
  74. data/app/services/workarea/global_e/custom_product_attribute.rb +19 -0
  75. data/app/services/workarea/global_e/discount.rb +215 -0
  76. data/app/services/workarea/global_e/merchant/brand.rb +21 -0
  77. data/app/services/workarea/global_e/merchant/category.rb +21 -0
  78. data/app/services/workarea/global_e/merchant/customer.rb +36 -0
  79. data/app/services/workarea/global_e/merchant/customer_details.rb +201 -0
  80. data/app/services/workarea/global_e/merchant/discount.rb +127 -0
  81. data/app/services/workarea/global_e/merchant/international_details.rb +296 -0
  82. data/app/services/workarea/global_e/merchant/order.rb +425 -0
  83. data/app/services/workarea/global_e/merchant/order_refund.rb +103 -0
  84. data/app/services/workarea/global_e/merchant/original_order.rb +28 -0
  85. data/app/services/workarea/global_e/merchant/parcel_tracking.rb +31 -0
  86. data/app/services/workarea/global_e/merchant/payment_details.rb +161 -0
  87. data/app/services/workarea/global_e/merchant/product.rb +222 -0
  88. data/app/services/workarea/global_e/merchant/refund_product.rb +69 -0
  89. data/app/services/workarea/global_e/merchant/response_info.rb +115 -0
  90. data/app/services/workarea/global_e/merchant_cart_product_attribute.rb +21 -0
  91. data/app/services/workarea/global_e/order_status.rb +20 -0
  92. data/app/services/workarea/global_e/order_status_details.rb +79 -0
  93. data/app/services/workarea/global_e/order_status_reason.rb +20 -0
  94. data/app/services/workarea/global_e/parcel.rb +53 -0
  95. data/app/services/workarea/global_e/product.rb +612 -0
  96. data/app/services/workarea/global_e/product_meta_data.rb +13 -0
  97. data/app/services/workarea/global_e/tracking_details.rb +23 -0
  98. data/app/services/workarea/global_e/update_order_dispatch_exception.rb +46 -0
  99. data/app/services/workarea/global_e/update_order_dispatch_request.rb +108 -0
  100. data/app/services/workarea/global_e/user_id_number_type.rb +21 -0
  101. data/app/services/workarea/global_e/users_details.rb +151 -0
  102. data/app/services/workarea/global_e/vat_category.rb +20 -0
  103. data/app/services/workarea/global_e/vat_rate_type.rb +27 -0
  104. data/app/services/workarea/save_order_analytics.decorator +18 -0
  105. data/app/view_models/workarea/admin/order_view_model.decorator +13 -0
  106. data/app/view_models/workarea/storefront/cart_view_model.decorator +7 -0
  107. data/app/view_models/workarea/storefront/order_item_view_model.decorator +16 -0
  108. data/app/view_models/workarea/storefront/order_view_model.decorator +45 -0
  109. data/app/view_models/workarea/storefront/product_view_model.decorator +35 -0
  110. data/app/views/workarea/admin/catalog_products/_country_exceptions_card.html.haml +31 -0
  111. data/app/views/workarea/admin/catalog_products/_global_e_attributes.html.haml +3 -0
  112. data/app/views/workarea/admin/catalog_products/_global_e_fields.html.haml +4 -0
  113. data/app/views/workarea/admin/country_exceptions/edit.html.haml +48 -0
  114. data/app/views/workarea/admin/country_exceptions/index.html.haml +47 -0
  115. data/app/views/workarea/admin/country_exceptions/new.html.haml +44 -0
  116. data/app/views/workarea/admin/fixed_prices/edit.html.haml +73 -0
  117. data/app/views/workarea/admin/fixed_prices/index.html.haml +55 -0
  118. data/app/views/workarea/admin/fixed_prices/new.html.haml +70 -0
  119. data/app/views/workarea/admin/orders/_global_e.html.haml +27 -0
  120. data/app/views/workarea/admin/orders/attributes.html.haml +131 -0
  121. data/app/views/workarea/admin/orders/global_e.html.haml +110 -0
  122. data/app/views/workarea/admin/orders/show.html.haml +27 -0
  123. data/app/views/workarea/admin/orders/tenders/_global_e_payment.html.haml +3 -0
  124. data/app/views/workarea/admin/pricing_skus/_cards.html.haml +98 -0
  125. data/app/views/workarea/storefront/cart_items/create.html.haml +71 -0
  126. data/app/views/workarea/storefront/carts/_pricing.html.haml +14 -0
  127. data/app/views/workarea/storefront/carts/show.html.haml +187 -0
  128. data/app/views/workarea/storefront/ge_checkouts/show.html.haml +1 -0
  129. data/app/views/workarea/storefront/global_e/_country_picker.html.haml +1 -0
  130. data/app/views/workarea/storefront/global_e/_head.html.haml +10 -0
  131. data/app/views/workarea/storefront/orders/_summary.html.haml +275 -0
  132. data/app/views/workarea/storefront/orders/tenders/_global_e_payment.html.haml +3 -0
  133. data/app/views/workarea/storefront/products/_pricing.html.haml +49 -0
  134. data/app/views/workarea/storefront/products/_restricted_item_text.html.haml +1 -0
  135. data/app/views/workarea/storefront/users/orders/_summary.html.haml +22 -0
  136. data/app/workers/workarea/global_e/update_order_dispatch.rb +28 -0
  137. data/app/workers/workarea/save_user_order_details.decorator +9 -0
  138. data/bin/rails +25 -0
  139. data/config/initializers/appends.rb +46 -0
  140. data/config/initializers/seeds.rb +1 -0
  141. data/config/initializers/workarea.rb +64 -0
  142. data/config/locales/en.yml +105 -0
  143. data/config/routes.rb +31 -0
  144. data/lib/workarea/global_e/engine.rb +10 -0
  145. data/lib/workarea/global_e/error.rb +8 -0
  146. data/lib/workarea/global_e/version.rb +5 -0
  147. data/lib/workarea/global_e.rb +58 -0
  148. data/script/admin_ci +5 -0
  149. data/script/ci +8 -0
  150. data/script/core_ci +5 -0
  151. data/script/plugins_ci +5 -0
  152. data/script/storefront_ci +5 -0
  153. data/test/dummy/.ruby-version +1 -0
  154. data/test/dummy/Rakefile +6 -0
  155. data/test/dummy/app/assets/config/manifest.js +3 -0
  156. data/test/dummy/app/assets/images/.keep +0 -0
  157. data/test/dummy/app/assets/javascripts/application.js +14 -0
  158. data/test/dummy/app/assets/stylesheets/application.css +15 -0
  159. data/test/dummy/app/controllers/application_controller.rb +2 -0
  160. data/test/dummy/app/controllers/concerns/.keep +0 -0
  161. data/test/dummy/app/helpers/application_helper.rb +2 -0
  162. data/test/dummy/app/jobs/application_job.rb +2 -0
  163. data/test/dummy/app/mailers/application_mailer.rb +4 -0
  164. data/test/dummy/app/models/concerns/.keep +0 -0
  165. data/test/dummy/app/views/layouts/application.html.erb +15 -0
  166. data/test/dummy/app/views/layouts/mailer.html.erb +13 -0
  167. data/test/dummy/app/views/layouts/mailer.text.erb +1 -0
  168. data/test/dummy/bin/bundle +3 -0
  169. data/test/dummy/bin/rails +4 -0
  170. data/test/dummy/bin/rake +4 -0
  171. data/test/dummy/bin/setup +28 -0
  172. data/test/dummy/bin/update +28 -0
  173. data/test/dummy/bin/yarn +11 -0
  174. data/test/dummy/config/application.rb +23 -0
  175. data/test/dummy/config/boot.rb +5 -0
  176. data/test/dummy/config/environment.rb +5 -0
  177. data/test/dummy/config/environments/development.rb +52 -0
  178. data/test/dummy/config/environments/production.rb +83 -0
  179. data/test/dummy/config/environments/test.rb +45 -0
  180. data/test/dummy/config/initializers/application_controller_renderer.rb +8 -0
  181. data/test/dummy/config/initializers/assets.rb +14 -0
  182. data/test/dummy/config/initializers/backtrace_silencers.rb +7 -0
  183. data/test/dummy/config/initializers/content_security_policy.rb +25 -0
  184. data/test/dummy/config/initializers/cookies_serializer.rb +5 -0
  185. data/test/dummy/config/initializers/filter_parameter_logging.rb +4 -0
  186. data/test/dummy/config/initializers/inflections.rb +16 -0
  187. data/test/dummy/config/initializers/mime_types.rb +4 -0
  188. data/test/dummy/config/initializers/workarea.rb +5 -0
  189. data/test/dummy/config/initializers/wrap_parameters.rb +9 -0
  190. data/test/dummy/config/locales/en.yml +33 -0
  191. data/test/dummy/config/puma.rb +34 -0
  192. data/test/dummy/config/routes.rb +5 -0
  193. data/test/dummy/config/secrets.yml +18 -0
  194. data/test/dummy/config/spring.rb +6 -0
  195. data/test/dummy/config.ru +5 -0
  196. data/test/dummy/db/seeds.rb +2 -0
  197. data/test/dummy/lib/assets/.keep +0 -0
  198. data/test/dummy/log/.keep +0 -0
  199. data/test/factories/workarea/global_e_factories.rb +836 -0
  200. data/test/integration/workarea/admin/catalog_product_country_exceptions_integration_test.rb +81 -0
  201. data/test/integration/workarea/admin/global_e_jump_to_integration_test.rb +20 -0
  202. data/test/integration/workarea/admin/pricing_sku_fixed_prices_integration_test.rb +83 -0
  203. data/test/integration/workarea/storefront/global_e_api/receive_order_integration_test.rb +278 -0
  204. data/test/integration/workarea/storefront/global_e_api/receive_order_refund_integration_test.rb +25 -0
  205. data/test/integration/workarea/storefront/global_e_api/receive_payment_integration_test.rb +34 -0
  206. data/test/integration/workarea/storefront/global_e_api/receive_shipping_info_integration_test.rb +29 -0
  207. data/test/integration/workarea/storefront/global_e_api/remove_restricted_products_integration_test.rb +27 -0
  208. data/test/integration/workarea/storefront/global_e_api/update_order_status_integration_test.rb +29 -0
  209. data/test/integration/workarea/storefront/global_e_checkout_cart_info/fixed_pricing_test.rb +438 -0
  210. data/test/integration/workarea/storefront/global_e_checkout_cart_info/gift_card_test.rb +63 -0
  211. data/test/integration/workarea/storefront/global_e_checkout_cart_info_integration_test.rb +660 -0
  212. data/test/integration/workarea/storefront/global_e_checkouts_integration_test.rb +71 -0
  213. data/test/integration/workarea/storefront/users/global_e_logins_integration_test.rb +20 -0
  214. data/test/models/workarea/catalog/product_global_e_test.rb +13 -0
  215. data/test/models/workarea/fixed_pricing_test.rb +117 -0
  216. data/test/models/workarea/global_e/country_exception_test.rb +36 -0
  217. data/test/models/workarea/payment_test.decorator +31 -0
  218. data/test/models/workarea/pricing/calculators/item_calculator_fixed_prices_test.rb +83 -0
  219. data/test/models/workarea/pricing/collection_fixed_prices_test.rb +83 -0
  220. data/test/models/workarea/pricing/price_distributor_test.decorator +21 -0
  221. data/test/models/workarea/pricing/sku_fixed_price_test.rb +133 -0
  222. data/test/support/workarea/global_e_support.rb +18 -0
  223. data/test/system/workarea/admin/global_e_system_test.rb +21 -0
  224. data/test/system/workarea/storefront/global_e_cart_system_test.rb +48 -0
  225. data/test/system/workarea/storefront/global_e_order_history_system_test.rb +43 -0
  226. data/test/teaspoon_env.rb +6 -0
  227. data/test/test_helper.rb +9 -0
  228. data/test/view_models/workarea/admin/global_e_order_view_model_test.rb +22 -0
  229. data/test/workers/workarea/global_e/update_order_dispatch_test.rb +64 -0
  230. data/test/workers/workarea/global_e_save_user_order_details_test.rb +41 -0
  231. data/workarea-global_e.gemspec +16 -0
  232. metadata +293 -0
@@ -0,0 +1,65 @@
1
+ module Workarea
2
+ decorate Pricing::Discount, with: :global_e do
3
+ # Fixed price orders can only handle percentage discounts or free gifts
4
+ # a future improvement would be for FlatOrPercentOff to localize the amount field
5
+ # to allow for fixed price orders to handle flat off amounts
6
+ #
7
+ def qualifies?(order)
8
+ return super unless order.fixed_pricing?
9
+ return super if is_percentage_discount? || is_free_gift?
10
+
11
+ false
12
+ end
13
+
14
+ # Build the data {Hash} used to create the price
15
+ # adjustment.
16
+ #
17
+ # This is the same method from Core except that the 0.to_m uses the same
18
+ # currency as `value`
19
+ #
20
+ # @param [Money] value
21
+ # @param [Integer] quantity
22
+ # @return [Hash]
23
+ #
24
+ def adjustment_data(value, quantity)
25
+ value = value.abs
26
+
27
+ {
28
+ price: self.class.price_level,
29
+ description: name,
30
+ calculator: self.class.name,
31
+ amount: 0.to_m(value.currency) - value,
32
+ quantity: quantity,
33
+ data: {
34
+ 'discount_id' => id.to_s,
35
+ 'discount_value' => value.to_f
36
+ }
37
+ }
38
+ end
39
+
40
+ def remove_from_items(items)
41
+ items.each do |item|
42
+ keepers = item.price_adjustments.reject do |adjustment|
43
+ adjustment.data['discount_id'] == id.to_s
44
+ end
45
+
46
+ international_keepers = item.international_price_adjustments.reject do |adjustment|
47
+ adjustment.data['discount_id'] == id.to_s
48
+ end
49
+
50
+ item.price_adjustments = keepers
51
+ item.international_price_adjustments = international_keepers
52
+ end
53
+ end
54
+
55
+ private
56
+
57
+ def is_percentage_discount?
58
+ self.is_a?(Workarea::Pricing::Discount::FlatOrPercentOff) && amount_type == :percent
59
+ end
60
+
61
+ def is_free_gift?
62
+ self.is_a?(Workarea::Pricing::Discount::FreeGift)
63
+ end
64
+ end
65
+ end
@@ -0,0 +1,37 @@
1
+ module Workarea
2
+ decorate Pricing::PriceDistributor, with: :global_e do
3
+ def initialize(total_value, units)
4
+ @currency = total_value.currency
5
+ @total_value = total_value
6
+ @units = units
7
+ @total_price = units.sum { |u| u[:price] }
8
+ end
9
+
10
+ def distributed_results
11
+ tmp = Hash.new(0.to_m(@currency))
12
+
13
+ @units.each do |unit|
14
+ next if @total_value.to_f.zero? ||
15
+ unit[:price].to_f.zero? ||
16
+ @total_price.to_f.zero?
17
+
18
+ unit_value = @total_value.to_f *
19
+ (unit[:price].to_f / @total_price.to_f)
20
+
21
+ @total_price -= unit[:price]
22
+ @total_value -= unit_value.to_m(@currency)
23
+
24
+ tmp[unit[:id]] += unit_value.to_m(@currency)
25
+ end
26
+
27
+ tmp
28
+ end
29
+
30
+ def empty_results
31
+ @units.inject({}) do |memo, unit|
32
+ memo[unit[:id]] ||= 0.to_m(@currency)
33
+ memo
34
+ end
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,17 @@
1
+ module Workarea
2
+ decorate Pricing::Request, with: :global_e do
3
+ private
4
+ def clone_order_attributes
5
+ attributes = @persisted_order.as_document.except('_id','id')
6
+
7
+ if attributes['items'].present?
8
+ attributes['items'].each do |item|
9
+ item['price_adjustments'] = []
10
+ item['international_price_adjustments'] = []
11
+ end
12
+ end
13
+
14
+ attributes
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,17 @@
1
+ module Workarea
2
+ decorate Pricing::Sku, with: :global_e do
3
+ decorated do
4
+ embeds_many :fixed_prices, class_name: "Workarea::GlobalE::FixedPrice", inverse_of: :pricing_sku
5
+ end
6
+
7
+ # Find the Fixed Price for this country currency combination, or for just the
8
+ # currency otherwise returns nil
9
+ #
10
+ # @return [Workarea::GlobalE::FixedPrice, nil]
11
+ #
12
+ def fixed_price_for(currency_code:, country: nil)
13
+ fixed_prices.find_by(currency_code: currency_code, country: country) rescue nil ||
14
+ fixed_prices.find_by(currency_code: currency_code) rescue nil
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,11 @@
1
+ module Workarea
2
+ decorate Search::Admin::Order, with: :global_e do
3
+ def keywords
4
+ super + [model.global_e_id].compact
5
+ end
6
+
7
+ def search_text
8
+ [super, model.global_e_id].compact.join(' ')
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,23 @@
1
+ module Workarea
2
+ decorate Shipping::Sku, with: :global_e do
3
+ def height
4
+ dimensions.first
5
+ end
6
+
7
+ def width
8
+ dimensions.second
9
+ end
10
+
11
+ def length
12
+ dimensions.third
13
+ end
14
+
15
+ def length_units
16
+ Workarea.config.shipping_options[:units] == :imperial ? :inches : :centimeters
17
+ end
18
+
19
+ def weight_units
20
+ Workarea.config.shipping_options[:units] == :imperial ? :ounces : :grams
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,11 @@
1
+ module Workarea
2
+ decorate Shipping, with: :global_e do
3
+ decorated do
4
+ field :international_shipping_total, type: Money
5
+
6
+ embeds_many :international_price_adjustments,
7
+ class_name: 'Workarea::PriceAdjustment',
8
+ extend: PriceAdjustmentExtension
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,10 @@
1
+ module Workarea
2
+ decorate User, with: :global_e do
3
+ decorated do
4
+ # @!attribute global_e_culture_code
5
+ # @return [String] the users prefered culture_code example: en-US
6
+ #
7
+ field :global_e_culture_code, type: String
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,66 @@
1
+ module Workarea
2
+ class GlobalESeeds
3
+ def perform
4
+ puts 'Adding fixed prices...'
5
+ add_fixed_prices
6
+ puts 'Adding country exceptions...'
7
+ add_country_exceptions
8
+ end
9
+
10
+ private
11
+
12
+ def add_fixed_prices
13
+ Pricing::Sku.all.each_by(100) do |pricing_sku|
14
+ price = pricing_sku.find_price
15
+
16
+ pricing_sku.fixed_prices.create!(
17
+ currency_code: "EUR",
18
+ regular: convert_price(price.regular),
19
+ sale: convert_price(price.sale),
20
+ msrp: convert_price(pricing_sku.msrp)
21
+ )
22
+
23
+ pricing_sku.fixed_prices.create!(
24
+ currency_code: "CAD",
25
+ regular: convert_price(price.regular, 1.1, "CAD"),
26
+ sale: convert_price(price.sale, 1.1, "CAD"),
27
+ msrp: convert_price(pricing_sku.msrp, 1.1, "CAD")
28
+ )
29
+
30
+ pricing_sku.fixed_prices.create!(
31
+ country: Country['AT'],
32
+ currency_code: "EUR",
33
+ regular: convert_price(price.regular, 1.3),
34
+ sale: convert_price(price.sale, 1.3),
35
+ msrp: convert_price(pricing_sku.msrp, 1.3)
36
+ )
37
+
38
+ pricing_sku.fixed_prices.create!(
39
+ country: Country['FR'],
40
+ currency_code: "EUR",
41
+ regular: convert_price(price.regular, 1.4),
42
+ sale: convert_price(price.sale, 1.4),
43
+ msrp: convert_price(pricing_sku.msrp, 1.4)
44
+ )
45
+ end
46
+ end
47
+
48
+ def convert_price(money, rate = 1.2, currency_code = "EUR")
49
+ return unless money.present?
50
+
51
+ fractional = (money.dup * rate).fractional
52
+ remainder = fractional % 500
53
+
54
+ Money.from_amount((fractional + 500 - remainder) / 100, currency_code)
55
+ end
56
+
57
+ def add_country_exceptions
58
+ Catalog::Product.all.each_by(100) do |product|
59
+ product.country_exceptions.create!(
60
+ country: Country['DE'],
61
+ restricted: true
62
+ )
63
+ end
64
+ end
65
+ end
66
+ end
@@ -0,0 +1,12 @@
1
+ module Workarea
2
+ decorate CreateFulfillment, with: :global_e do
3
+ def initialize(order, global_e: false)
4
+ @order = order
5
+ @global_e = global_e
6
+ end
7
+
8
+ def fulfillment
9
+ @fulfillment ||= super.tap { |f| f.global_e = @global_e }
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,218 @@
1
+ module Workarea
2
+ module GlobalE
3
+ class AddressDetails
4
+ attr_reader :user, :address
5
+
6
+ def initialize(user, address)
7
+ @user = user
8
+ @address = address
9
+ end
10
+
11
+ def as_json(*args)
12
+ {
13
+ UserIdNumber: user_id_number,
14
+ UserIdNumberType: user_id_number_type,
15
+ FirstName: first_name,
16
+ LastName: last_name,
17
+ MiddleName: middle_name,
18
+ Salutation: salutation,
19
+ Phone1: phone1,
20
+ Phone2: phone2,
21
+ Fax: fax,
22
+ Email: email,
23
+ Company: company,
24
+ Address1: address1,
25
+ Address2: address2,
26
+ City: city,
27
+ StateOrProvice: state_or_province,
28
+ StateCode: state_code,
29
+ Zip: zip,
30
+ CountryCode: country_code,
31
+ IsShipping: is_shipping,
32
+ IsBilling: is_billing,
33
+ IsDefaultShipping: is_default_shipping,
34
+ IsDefaultBilling: is_default_billing,
35
+ AddressBookId: address_book_id
36
+ }.compact
37
+ end
38
+
39
+ # User’s personal ID document number
40
+ #
41
+ # @return [String]
42
+ #
43
+ def user_id_number
44
+ end
45
+
46
+ # User’s personal ID document type (e.g. Passport, ID card, etc.)
47
+ #
48
+ # UserIdNumberType
49
+ #
50
+ def user_id_number_type
51
+ end
52
+
53
+ # First name
54
+ #
55
+ # @return [String]
56
+ #
57
+ def first_name
58
+ address.first_name
59
+ end
60
+
61
+ # Last name
62
+ #
63
+ # @return [String]
64
+ #
65
+ def last_name
66
+ address.last_name
67
+ end
68
+
69
+ # Middle name
70
+ #
71
+ # @return [String
72
+ #
73
+ def middle_name
74
+ end
75
+
76
+ # Salutation or title (e.g. Dr., Mr., etc.)
77
+ #
78
+ # @return [String]
79
+ #
80
+ def salutation
81
+ end
82
+
83
+ # Phone 1
84
+ #
85
+ # @return [String]
86
+ #
87
+ def phone1
88
+ address.phone_number
89
+ end
90
+
91
+ # Phone 2
92
+ #
93
+ # @return [String]
94
+ #
95
+ def phone2
96
+ end
97
+
98
+ # Fax
99
+ #
100
+ # @return [String]
101
+ #
102
+ def fax
103
+ end
104
+
105
+ # E-mail address
106
+ #
107
+ # @return [String]
108
+ #
109
+ def email
110
+ user.email
111
+ end
112
+
113
+ # Company name
114
+ #
115
+ # @return [String]
116
+ #
117
+ def company
118
+ address.company
119
+ end
120
+
121
+ # Address line 1
122
+ #
123
+ # @return [String]
124
+ #
125
+ def address1
126
+ address.street
127
+ end
128
+
129
+ # Address line 2
130
+ #
131
+ # @return [String]
132
+ #
133
+ def address2
134
+ address.street_2
135
+ end
136
+
137
+ # City name
138
+ #
139
+ # @return [String]
140
+ #
141
+ def city
142
+ address.city
143
+ end
144
+
145
+ # State or province name
146
+ #
147
+ # @return [String]
148
+ #
149
+ def state_or_province
150
+ address.country.subdivisions[address.region].name rescue nil
151
+ end
152
+
153
+ # State or province ISO code such as AZ for Arizona (if applicable)
154
+ #
155
+ # @return [String]
156
+ #
157
+ def state_code
158
+ address.region
159
+ end
160
+
161
+ # Zip or postal code
162
+ #
163
+ # @return [String]
164
+ #
165
+ def zip
166
+ address.postal_code
167
+ end
168
+
169
+ # 2-char ISO country code
170
+ #
171
+ # @return [String]
172
+ #
173
+ def country_code
174
+ address.country.alpha2
175
+ end
176
+
177
+ # Indicates that the current address can be used as a shipping address
178
+ #
179
+ # @return [Boolean]
180
+ #
181
+ def is_shipping
182
+ address.last_shipped_at.present?
183
+ end
184
+
185
+ # Indicates that the current address can be used as a billing address
186
+ #
187
+ # @return [Boolean]
188
+ #
189
+ def is_billing
190
+ address.last_billed_at.present?
191
+ end
192
+
193
+ # Indicates that the current address is the default shipping address
194
+ #
195
+ # @return [Boolean]
196
+ #
197
+ def is_default_shipping
198
+ user.default_shipping_address == address
199
+ end
200
+
201
+ # Indicates that the current address is the default billing address
202
+ #
203
+ # @return [Boolean]
204
+ #
205
+ def is_default_billing
206
+ user.default_billing_address == address
207
+ end
208
+
209
+ # Id of the current address from within the address book
210
+ #
211
+ # @return [String]
212
+ #
213
+ def address_book_id
214
+ address.id.to_s
215
+ end
216
+ end
217
+ end
218
+ end
@@ -0,0 +1,45 @@
1
+ module Workarea
2
+ module GlobalE
3
+ module Api
4
+ class NotifyOrderRefunded
5
+ attr_reader :order, :order_refund
6
+
7
+ def initialize(order, order_refund)
8
+ @order = order
9
+ @order_refund = order_refund
10
+ end
11
+
12
+ def response
13
+ @response ||=
14
+ begin
15
+ refund_items
16
+ Merchant::ResponseInfo.new(order: order)
17
+ end
18
+ end
19
+
20
+ private
21
+
22
+ def fulfillment
23
+ @fulfillment ||= Fulfillment.find order.id
24
+ end
25
+
26
+ def refunded_items
27
+ order_refund.products.map do |refund_product|
28
+ {
29
+ id: refund_product.cart_item_id.to_s,
30
+ quantity: refund_product.refund_quantity,
31
+ original_refund_amount: refund_product.original_refund_amount.to_m,
32
+ refund_amount: refund_product.original_refund_amount.to_m(order.currency),
33
+ refund_reason: refund_product.refund_reason.to_h,
34
+ comment: refund_product.refund_comments
35
+ }
36
+ end
37
+ end
38
+
39
+ def refund_items
40
+ fulfillment.refund_items refunded_items
41
+ end
42
+ end
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,46 @@
1
+ module Workarea
2
+ module GlobalE
3
+ module Api
4
+ class PerformOrderPayment
5
+ attr_reader :order, :merchant_order
6
+
7
+ def initialize(order, merchant_order)
8
+ @order = order
9
+ @merchant_order = merchant_order
10
+ end
11
+
12
+ def response
13
+ @response ||=
14
+ begin
15
+ order.global_e_approve!
16
+ update_payment
17
+ update_fulfillment
18
+ Workarea::GlobalE::Merchant::ResponseInfo.new(order: order)
19
+ end
20
+ end
21
+
22
+ private
23
+
24
+ def update_fulfillment
25
+ fulfillment.update_attributes(
26
+ global_e_tracking_url: merchant_order.international_details&.order_tracking_url
27
+ )
28
+ end
29
+
30
+ def fulfillment
31
+ @fulfillment ||= Fulfillment.find order.id
32
+ end
33
+
34
+ def update_payment
35
+ payment.with(write: { w: "majority", j: true }) do
36
+ payment.update_attributes!(global_e_approved_at: Time.current)
37
+ end
38
+ end
39
+
40
+ def payment
41
+ @payment ||= Workarea::Payment.find order.id
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
@@ -0,0 +1,28 @@
1
+ module Workarea
2
+ module GlobalE
3
+ module Api
4
+ class RemoveRestrictedProducts
5
+ attr_reader :order, :codes
6
+
7
+ def initialize(order, codes = [])
8
+ @order = order
9
+ @codes = codes
10
+ end
11
+
12
+ def self.perform(*args)
13
+ new(*args).tap(&:call)
14
+ end
15
+
16
+ def call
17
+ order.items.each do |item|
18
+ item.destroy if item.sku.in?(codes)
19
+ end
20
+ end
21
+
22
+ def response
23
+ @response ||= Merchant::ResponseInfo.new(order: order)
24
+ end
25
+ end
26
+ end
27
+ end
28
+ end