workarea-core 3.4.44 → 3.5.0.beta.1

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 (427) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE.txt +52 -0
  3. data/app/assets/javascripts/workarea/core/modules/duplicate_id.js +1 -5
  4. data/app/assets/javascripts/workarea/core/modules/style_guide_autocomplete_fields.js +9 -42
  5. data/app/assets/javascripts/workarea/core/modules/url.js +14 -0
  6. data/app/controllers/workarea/application_controller.rb +5 -1
  7. data/app/controllers/workarea/authentication.rb +15 -26
  8. data/app/controllers/workarea/authorization.rb +3 -3
  9. data/app/controllers/workarea/current_referrer.rb +1 -2
  10. data/app/controllers/workarea/current_release.rb +1 -1
  11. data/app/controllers/workarea/current_segments.rb +52 -0
  12. data/app/controllers/workarea/current_tracking.rb +45 -0
  13. data/app/controllers/workarea/http_caching.rb +30 -0
  14. data/app/controllers/workarea/impersonation.rb +18 -44
  15. data/app/helpers/workarea/schema_org_helper.rb +21 -0
  16. data/app/mailers/workarea/application_mailer.rb +2 -4
  17. data/app/middleware/workarea/application_middleware.rb +44 -0
  18. data/app/middleware/workarea/query_cache_middleware.rb +55 -0
  19. data/app/middleware/workarea/release_server_middleware.rb +1 -1
  20. data/app/models/workarea/application_document.rb +1 -1
  21. data/app/models/workarea/bulk_action/product_edit.rb +6 -6
  22. data/app/models/workarea/calculate_percent_change.rb +1 -1
  23. data/app/models/workarea/catalog/category.rb +0 -2
  24. data/app/models/workarea/catalog/product.rb +19 -2
  25. data/app/models/workarea/checkout.rb +18 -6
  26. data/app/models/workarea/checkout/collect_payment.rb +10 -1
  27. data/app/models/workarea/checkout/fraud/analyzer.rb +44 -0
  28. data/app/models/workarea/checkout/fraud/no_decision_analyzer.rb +14 -0
  29. data/app/models/workarea/checkout/fraud/test_analyzer.rb +26 -0
  30. data/app/models/workarea/configuration/admin.rb +25 -0
  31. data/app/models/workarea/configuration/params.rb +45 -0
  32. data/app/models/workarea/content.rb +12 -82
  33. data/app/models/workarea/content/asset.rb +5 -18
  34. data/app/models/workarea/content/block.rb +8 -2
  35. data/app/models/workarea/content/block_draft.rb +7 -2
  36. data/app/models/workarea/content/block_type.rb +2 -2
  37. data/app/models/workarea/content/block_type_definition.rb +4 -0
  38. data/app/models/workarea/content/preset.rb +1 -1
  39. data/app/models/workarea/data_file/csv.rb +6 -8
  40. data/app/models/workarea/data_file/import.rb +9 -1
  41. data/app/models/workarea/data_file/json.rb +1 -20
  42. data/app/models/workarea/data_file/operation.rb +0 -4
  43. data/app/models/workarea/data_file/tax_rates.rb +3 -0
  44. data/app/models/workarea/featured_products.rb +8 -0
  45. data/app/models/workarea/fulfillment/policies/base.rb +21 -0
  46. data/app/models/workarea/fulfillment/policies/download.rb +21 -0
  47. data/app/models/workarea/fulfillment/policies/ignore.rb +11 -0
  48. data/app/models/workarea/fulfillment/policies/ship.rb +15 -0
  49. data/app/models/workarea/fulfillment/sku.rb +72 -0
  50. data/app/models/workarea/fulfillment/token.rb +36 -0
  51. data/app/models/workarea/inquiry.rb +1 -2
  52. data/app/models/workarea/insights/customer_acquisition.rb +5 -9
  53. data/app/models/workarea/insights/trending_products.rb +2 -2
  54. data/app/models/workarea/insights/trending_searches.rb +2 -2
  55. data/app/models/workarea/inventory/collection.rb +30 -0
  56. data/app/models/workarea/inventory/collection_status.rb +40 -0
  57. data/app/models/workarea/metrics/affinity.rb +33 -0
  58. data/app/models/workarea/metrics/country_by_day.rb +4 -0
  59. data/app/models/workarea/metrics/product_by_day.rb +3 -0
  60. data/app/models/workarea/metrics/product_by_week.rb +2 -0
  61. data/app/models/workarea/metrics/product_for_last_week.rb +8 -12
  62. data/app/models/workarea/metrics/sales_by_day.rb +5 -0
  63. data/app/models/workarea/metrics/search_by_day.rb +1 -3
  64. data/app/models/workarea/metrics/search_for_last_week.rb +5 -11
  65. data/app/models/workarea/metrics/segment_by_day.rb +31 -0
  66. data/app/models/workarea/metrics/sku_by_day.rb +3 -0
  67. data/app/models/workarea/metrics/tender_by_day.rb +11 -0
  68. data/app/models/workarea/metrics/update_user_aggregations.rb +77 -0
  69. data/app/models/workarea/metrics/user.rb +73 -87
  70. data/app/models/workarea/navigation/breadcrumbs.rb +10 -1
  71. data/app/models/workarea/order.rb +47 -4
  72. data/app/models/workarea/order/fraud_decision.rb +18 -0
  73. data/app/models/workarea/order/item.rb +5 -0
  74. data/app/models/workarea/order/queries.rb +1 -0
  75. data/app/models/workarea/order/status.rb +10 -1
  76. data/app/models/workarea/payment.rb +7 -2
  77. data/app/models/workarea/payment/credit_card.rb +12 -0
  78. data/app/models/workarea/pricing/cache_key.rb +9 -3
  79. data/app/models/workarea/pricing/calculator.rb +5 -1
  80. data/app/models/workarea/pricing/calculators/tax_calculator.rb +32 -5
  81. data/app/models/workarea/pricing/discount.rb +2 -3
  82. data/app/models/workarea/pricing/discount/application_group.rb +8 -3
  83. data/app/models/workarea/pricing/discount/free_gift.rb +2 -1
  84. data/app/models/workarea/pricing/discount/redemption.rb +1 -1
  85. data/app/models/workarea/pricing/item_tax_applier.rb +41 -0
  86. data/app/models/workarea/pricing/price.rb +1 -0
  87. data/app/models/workarea/pricing/request.rb +11 -0
  88. data/app/models/workarea/pricing/sku.rb +1 -0
  89. data/app/models/workarea/pricing/tax_application.rb +21 -0
  90. data/app/models/workarea/pricing/tax_applier.rb +12 -15
  91. data/app/models/workarea/pricing/unsupported_segmentation.rb +22 -0
  92. data/app/models/workarea/product_rule.rb +5 -0
  93. data/app/models/workarea/releasable.rb +83 -89
  94. data/app/models/workarea/release.rb +72 -99
  95. data/app/models/workarea/release/activation.rb +45 -0
  96. data/app/models/workarea/release/changes.rb +45 -0
  97. data/app/models/workarea/release/changeset.rb +42 -52
  98. data/app/models/workarea/release/preview.rb +28 -0
  99. data/app/models/workarea/release/status.rb +2 -24
  100. data/app/models/workarea/release_session.rb +11 -11
  101. data/app/models/workarea/search/admin.rb +17 -39
  102. data/app/models/workarea/search/admin/catalog_product.rb +1 -2
  103. data/app/models/workarea/search/admin/fulfillment_sku.rb +27 -0
  104. data/app/models/workarea/search/admin/order.rb +1 -1
  105. data/app/models/workarea/search/admin/pricing_discount.rb +1 -1
  106. data/app/models/workarea/search/admin/release.rb +1 -4
  107. data/app/models/workarea/search/admin/segment.rb +19 -0
  108. data/app/models/workarea/search/order_text.rb +23 -6
  109. data/app/models/workarea/search/storefront.rb +33 -29
  110. data/app/models/workarea/search/storefront/category_query.rb +152 -0
  111. data/app/models/workarea/search/storefront/product/categories.rb +11 -45
  112. data/app/models/workarea/segment.rb +54 -0
  113. data/app/models/workarea/segment/first_time_customer.rb +8 -0
  114. data/app/models/workarea/segment/first_time_visitor.rb +12 -0
  115. data/app/models/workarea/segment/life_cycle.rb +44 -0
  116. data/app/models/workarea/segment/loyal_customer.rb +12 -0
  117. data/app/models/workarea/segment/returning_customer.rb +14 -0
  118. data/app/models/workarea/segment/returning_visitor.rb +12 -0
  119. data/app/models/workarea/segment/rules/base.rb +16 -0
  120. data/app/models/workarea/segment/rules/browser_info.rb +29 -0
  121. data/app/models/workarea/segment/rules/geolocation.rb +29 -0
  122. data/app/models/workarea/segment/rules/geolocation_option.rb +53 -0
  123. data/app/models/workarea/segment/rules/last_order.rb +14 -0
  124. data/app/models/workarea/segment/rules/logged_in.rb +13 -0
  125. data/app/models/workarea/segment/rules/orders.rb +17 -0
  126. data/app/models/workarea/segment/rules/revenue.rb +17 -0
  127. data/app/models/workarea/segment/rules/sessions.rb +17 -0
  128. data/app/models/workarea/segment/rules/tags.rb +14 -0
  129. data/app/models/workarea/segment/rules/traffic_referrer.rb +18 -0
  130. data/app/models/workarea/segmentable.rb +66 -0
  131. data/app/models/workarea/sort.rb +14 -2
  132. data/app/models/workarea/tax/rate.rb +35 -1
  133. data/app/models/workarea/user/authorization.rb +19 -13
  134. data/app/models/workarea/user/login.rb +4 -0
  135. data/app/models/workarea/user/password_reset.rb +1 -3
  136. data/app/queries/workarea/categorization.rb +3 -3
  137. data/app/queries/workarea/featured_categorization.rb +53 -0
  138. data/app/queries/workarea/order_cancellation_metrics.rb +155 -0
  139. data/app/queries/workarea/order_item_details.rb +16 -3
  140. data/app/queries/workarea/order_metrics.rb +32 -3
  141. data/app/queries/workarea/product_primary_navigation.rb +13 -2
  142. data/app/queries/workarea/product_releases.rb +38 -0
  143. data/app/queries/workarea/recommendation/user_activity_based.rb +14 -6
  144. data/app/queries/workarea/reports/average_order_value.rb +1 -1
  145. data/app/queries/workarea/reports/customers.rb +14 -11
  146. data/app/queries/workarea/reports/first_time_vs_returning_sales.rb +1 -1
  147. data/app/queries/workarea/reports/group_by_time.rb +13 -17
  148. data/app/queries/workarea/reports/sales_by_category.rb +1 -1
  149. data/app/queries/workarea/reports/sales_by_country.rb +10 -3
  150. data/app/queries/workarea/reports/sales_by_discount.rb +1 -1
  151. data/app/queries/workarea/reports/sales_by_menu.rb +1 -1
  152. data/app/queries/workarea/reports/sales_by_product.rb +39 -4
  153. data/app/queries/workarea/reports/sales_by_sku.rb +39 -4
  154. data/app/queries/workarea/reports/sales_by_tender.rb +42 -0
  155. data/app/queries/workarea/reports/sales_by_traffic_referrer.rb +1 -1
  156. data/app/queries/workarea/reports/sales_over_time.rb +10 -3
  157. data/app/queries/workarea/reports/searches.rb +1 -1
  158. data/app/queries/workarea/reports/searches_over_time.rb +1 -1
  159. data/app/queries/workarea/reports/searches_without_results_over_time.rb +1 -1
  160. data/app/queries/workarea/search/admin_fulfillment_skus.rb +20 -0
  161. data/app/queries/workarea/search/admin_releases.rb +1 -4
  162. data/app/queries/workarea/search/admin_search.rb +0 -4
  163. data/app/queries/workarea/search/admin_segments.rb +16 -0
  164. data/app/queries/workarea/search/admin_sorting.rb +1 -1
  165. data/app/queries/workarea/search/pagination.rb +1 -4
  166. data/app/queries/workarea/search/product_display_rules.rb +40 -8
  167. data/app/queries/workarea/search/product_entries.rb +15 -1
  168. data/app/queries/workarea/search/product_search.rb +4 -1
  169. data/app/queries/workarea/search/storefront_search.rb +5 -4
  170. data/app/queries/workarea/search/storefront_search/exact_matches.rb +1 -1
  171. data/app/queries/workarea/search/storefront_search/response.rb +6 -4
  172. data/app/seeds/workarea/assets_seeds.rb +2 -1
  173. data/app/seeds/workarea/insights_seeds.rb +0 -23
  174. data/app/seeds/workarea/orders_seeds.rb +7 -6
  175. data/app/seeds/workarea/products_seeds.rb +2 -0
  176. data/app/seeds/workarea/segments_seeds.rb +8 -0
  177. data/app/seeds/workarea/tax_seeds.rb +3 -3
  178. data/app/services/workarea/cancel_order.rb +8 -3
  179. data/app/services/workarea/copy_order.rb +6 -0
  180. data/app/services/workarea/create_fulfillment.rb +5 -3
  181. data/app/services/workarea/direct_upload.rb +11 -19
  182. data/app/services/workarea/hash_update.rb +1 -18
  183. data/app/services/workarea/packaging.rb +1 -1
  184. data/app/services/workarea/save_publishing.rb +5 -1
  185. data/app/workers/sidekiq/callbacks.rb +4 -52
  186. data/app/workers/sidekiq/callbacks_worker.rb +4 -6
  187. data/app/workers/workarea/bulk_index_admin.rb +2 -2
  188. data/app/workers/workarea/bulk_index_products.rb +6 -5
  189. data/app/workers/workarea/bulk_index_searches.rb +5 -5
  190. data/app/workers/workarea/deactivate_stale_discounts.rb +3 -3
  191. data/app/workers/workarea/generate_insights.rb +1 -1
  192. data/app/workers/workarea/index_admin_search.rb +1 -0
  193. data/app/workers/workarea/index_categorization.rb +4 -7
  194. data/app/workers/workarea/index_category.rb +2 -1
  195. data/app/workers/workarea/index_category_changes.rb +11 -6
  196. data/app/workers/workarea/index_fulfillment_changes.rb +2 -1
  197. data/app/workers/workarea/index_help.rb +2 -1
  198. data/app/workers/workarea/index_page.rb +2 -1
  199. data/app/workers/workarea/index_payment_transactions.rb +2 -1
  200. data/app/workers/workarea/index_product.rb +4 -4
  201. data/app/workers/workarea/index_product_children.rb +4 -3
  202. data/app/workers/workarea/index_product_rule.rb +3 -2
  203. data/app/workers/workarea/index_search_customizations.rb +3 -2
  204. data/app/workers/workarea/index_skus.rb +5 -6
  205. data/app/workers/workarea/keep_product_index_fresh.rb +3 -5
  206. data/app/workers/workarea/process_import.rb +3 -3
  207. data/app/workers/workarea/process_search_recommendations.rb +5 -9
  208. data/app/workers/workarea/publish_release.rb +1 -0
  209. data/app/workers/workarea/save_metrics.rb +116 -0
  210. data/app/workers/workarea/save_order_cancellation_metrics.rb +35 -0
  211. data/app/workers/workarea/save_order_metrics.rb +10 -74
  212. data/app/workers/workarea/status_reporter.rb +2 -4
  213. data/app/workers/workarea/synchronize_user_metrics.rb +17 -0
  214. data/app/workers/workarea/update_payment_profile_email.rb +22 -0
  215. data/app/workers/workarea/verify_scheduled_releases.rb +4 -11
  216. data/config/initializers/00_configuration.rb +185 -0
  217. data/config/initializers/02_assets.rb +1 -0
  218. data/config/initializers/05_scheduled_jobs.rb +0 -7
  219. data/config/initializers/10_rack_middleware.rb +2 -5
  220. data/config/initializers/11_payment.rb +4 -0
  221. data/config/initializers/13_rack_attack.rb +2 -4
  222. data/config/initializers/14_content_block_types.rb +16 -16
  223. data/config/initializers/15_endpoint_monitoring.rb +3 -6
  224. data/config/initializers/{21_premailer.rb → 24_premailer.rb} +1 -0
  225. data/config/initializers/{20_i18n_js.rb → 25_i18n_js.rb} +0 -0
  226. data/config/locales/en.yml +13 -24
  227. data/lib/generators/workarea/content_block_type/templates/initializer.rb +1 -1
  228. data/lib/generators/workarea/install/USAGE +0 -1
  229. data/lib/generators/workarea/install/install_generator.rb +0 -21
  230. data/lib/generators/workarea/install/templates/initializer.rb.erb +1 -1
  231. data/lib/tasks/insights.rake +1 -0
  232. data/lib/tasks/migrate.rake +106 -0
  233. data/lib/tasks/search.rake +17 -19
  234. data/lib/tasks/tests.rake +1 -1
  235. data/lib/workarea.rb +102 -3
  236. data/lib/workarea/cache.rb +6 -35
  237. data/lib/workarea/changelog.rake +2 -2
  238. data/lib/workarea/configuration.rb +121 -148
  239. data/lib/workarea/configuration/administrable/definition.rb +42 -0
  240. data/lib/workarea/configuration/administrable/field.rb +79 -0
  241. data/lib/workarea/configuration/administrable/fieldset.rb +44 -0
  242. data/lib/workarea/configuration/administrable_options.rb +24 -0
  243. data/lib/workarea/configuration/cache_store.rb +3 -1
  244. data/lib/workarea/configuration/content_blocks.rb +17 -0
  245. data/lib/workarea/configuration/mongoid.rb +1 -4
  246. data/lib/workarea/configuration/session.rb +36 -0
  247. data/lib/workarea/configuration/sidekiq.rb +3 -1
  248. data/lib/workarea/core.rb +15 -11
  249. data/lib/workarea/core/engine.rb +3 -58
  250. data/lib/workarea/elasticsearch/document.rb +8 -15
  251. data/lib/workarea/ext/freedom_patches/action_view_cache_helper.rb +4 -6
  252. data/lib/workarea/ext/freedom_patches/active_support_duration.rb +14 -0
  253. data/lib/workarea/ext/freedom_patches/money.rb +11 -0
  254. data/lib/workarea/ext/freedom_patches/premailer.rb +6 -0
  255. data/lib/workarea/ext/freedom_patches/string.rb +19 -4
  256. data/lib/workarea/ext/mongoid/find_ordered.rb +2 -2
  257. data/lib/workarea/ext/mongoid/lookup_hash.rb +30 -0
  258. data/lib/workarea/geolocation.rb +24 -6
  259. data/lib/workarea/routes_constraints/super_admin.rb +1 -1
  260. data/lib/workarea/version.rb +3 -4
  261. data/lib/workarea/visit.rb +92 -0
  262. data/lib/workarea/warnings.rb +95 -0
  263. data/test/dummy/config/initializers/session_store.rb +1 -1
  264. data/test/fixtures/tax_rates.csv +3 -3
  265. data/test/generators/workarea/content_block_type_generator_test.rb +1 -1
  266. data/test/generators/workarea/install_generator_test.rb +0 -13
  267. data/test/integration/workarea/authentication_test.rb +27 -4
  268. data/test/integration/workarea/authorization_test.rb +5 -0
  269. data/test/integration/workarea/cache_varies_integration_test.rb +21 -23
  270. data/test/integration/workarea/monitoring_integration_test.rb +5 -10
  271. data/test/javascripts/duplicate_id_spec.js +1 -7
  272. data/test/javascripts/fixtures/{duplicate_id_fail.html.haml → duplicate_id.html.haml} +0 -1
  273. data/test/javascripts/form_submitting_controls_spec.js +0 -1
  274. data/test/lib/workarea/asset_endpoints/favicons_test.rb +11 -13
  275. data/test/lib/workarea/configuration/administrable/definition_test.rb +71 -0
  276. data/test/lib/workarea/configuration/administrable/field_test.rb +128 -0
  277. data/test/lib/workarea/configuration/administrable/fieldset_test.rb +78 -0
  278. data/test/lib/workarea/configuration/configuration_test.rb +20 -0
  279. data/test/lib/workarea/elasticsearch/document_test.rb +0 -20
  280. data/test/lib/workarea/elasticsearch/query_cache_test.rb +7 -7
  281. data/test/lib/workarea/ext/freedom_patches/money_test.rb +11 -0
  282. data/test/lib/workarea/ext/mongoid/lookup_hash_test.rb +86 -0
  283. data/test/lib/workarea/geolocation_test.rb +20 -0
  284. data/test/mailers/workarea/application_mailer_test.rb +1 -11
  285. data/test/middleware/workarea/query_cache_middleware_test.rb +55 -0
  286. data/test/models/workarea/checkout/collect_payment_test.rb +14 -6
  287. data/test/models/workarea/checkout_test.rb +31 -57
  288. data/test/models/workarea/configuration/params_test.rb +37 -0
  289. data/test/models/workarea/data_file/csv_test.rb +8 -73
  290. data/test/models/workarea/data_file/import_test.rb +31 -0
  291. data/test/models/workarea/data_file/json_test.rb +6 -48
  292. data/test/models/workarea/data_file/tax_test.rb +3 -0
  293. data/test/models/workarea/fulfillment/policies/download_test.rb +39 -0
  294. data/test/models/workarea/fulfillment/sku_test.rb +54 -0
  295. data/test/models/workarea/insights/best_customers_test.rb +5 -2
  296. data/test/models/workarea/insights/best_full_price_customers_test.rb +5 -2
  297. data/test/models/workarea/insights/customer_acquisition_test.rb +1 -1
  298. data/test/models/workarea/insights/customers_at_risk_test.rb +1 -1
  299. data/test/models/workarea/insights/low_aov_customers_test.rb +1 -1
  300. data/test/models/workarea/inventory/collection_test.rb +75 -0
  301. data/test/models/workarea/metrics/affinity_test.rb +85 -0
  302. data/test/models/workarea/metrics/product_by_week_test.rb +27 -31
  303. data/test/models/workarea/metrics/search_by_day_test.rb +3 -0
  304. data/test/models/workarea/metrics/search_by_week_test.rb +27 -31
  305. data/test/models/workarea/metrics/update_user_aggregations_test.rb +62 -0
  306. data/test/models/workarea/metrics/user_test.rb +146 -63
  307. data/test/models/workarea/navigation/breadcrumbs_test.rb +12 -2
  308. data/test/models/workarea/order/queries_test.rb +2 -0
  309. data/test/models/workarea/order_test.rb +44 -0
  310. data/test/models/workarea/payment/address_test.rb +109 -111
  311. data/test/models/workarea/payment/credit_card_integration_test.rb +0 -52
  312. data/test/models/workarea/payment/credit_card_test.rb +5 -0
  313. data/test/models/workarea/pricing/cache_key_test.rb +7 -1
  314. data/test/models/workarea/pricing/calculators/tax_calculator_test.rb +41 -1
  315. data/test/models/workarea/pricing/discount/collection_test.rb +27 -29
  316. data/test/models/workarea/pricing/discount_test.rb +22 -24
  317. data/test/models/workarea/pricing/item_tax_applier_test.rb +83 -0
  318. data/test/models/workarea/pricing/price_test.rb +9 -0
  319. data/test/models/workarea/pricing/request_test.rb +13 -0
  320. data/test/models/workarea/pricing/sku_test.rb +9 -0
  321. data/test/models/workarea/releasable_active_test.rb +113 -0
  322. data/test/models/workarea/releasable_test.rb +69 -120
  323. data/test/models/workarea/release/changeset_test.rb +41 -0
  324. data/test/models/workarea/release_jobs_test.rb +52 -0
  325. data/test/models/workarea/release_previewing_test.rb +43 -0
  326. data/test/models/workarea/release_test.rb +59 -153
  327. data/test/models/workarea/search/admin/content_asset_test.rb +26 -28
  328. data/test/models/workarea/search/order_text_test.rb +35 -0
  329. data/test/models/workarea/search/storefront/category_query_test.rb +81 -0
  330. data/test/models/workarea/search/storefront/product/categories_test.rb +10 -70
  331. data/test/models/workarea/search/storefront/product_test.rb +10 -11
  332. data/test/models/workarea/search/storefront_test.rb +1 -13
  333. data/test/models/workarea/segment/life_cycle_test.rb +24 -0
  334. data/test/models/workarea/segment/rules/browser_info_test.rb +33 -0
  335. data/test/models/workarea/segment/rules/geolocation_option_test.rb +16 -0
  336. data/test/models/workarea/segment/rules/geolocation_test.rb +49 -0
  337. data/test/models/workarea/segment/rules/last_order_test.rb +32 -0
  338. data/test/models/workarea/segment/rules/logged_in_test.rb +25 -0
  339. data/test/models/workarea/segment/rules/orders_test.rb +59 -0
  340. data/test/models/workarea/segment/rules/revenue_test.rb +59 -0
  341. data/test/models/workarea/segment/rules/sessions_test.rb +26 -0
  342. data/test/models/workarea/segment/rules/tags_test.rb +27 -0
  343. data/test/models/workarea/segment/rules/traffic_referrer_test.rb +31 -0
  344. data/test/models/workarea/segment_test.rb +80 -0
  345. data/test/models/workarea/segmentable_test.rb +74 -0
  346. data/test/models/workarea/shipping/address_test.rb +109 -111
  347. data/test/models/workarea/shipping/sku_test.rb +8 -12
  348. data/test/models/workarea/user/password_reset_test.rb +4 -12
  349. data/test/models/workarea/user_test.rb +13 -10
  350. data/test/queries/workarea/admin_search_query_wrapper_test.rb +21 -25
  351. data/test/queries/workarea/categorization_test.rb +49 -0
  352. data/test/queries/workarea/featured_categorization_test.rb +66 -0
  353. data/test/queries/workarea/order_cancellation_metrics_test.rb +203 -0
  354. data/test/queries/workarea/order_item_details_test.rb +17 -0
  355. data/test/queries/workarea/order_metrics_test.rb +12 -0
  356. data/test/queries/workarea/product_releases_test.rb +56 -0
  357. data/test/queries/workarea/recommendation/searches_test.rb +3 -3
  358. data/test/queries/workarea/recommendation/user_activity_based_test.rb +4 -4
  359. data/test/queries/workarea/reports/customers_test.rb +12 -8
  360. data/test/queries/workarea/reports/report_test.rb +4 -6
  361. data/test/queries/workarea/reports/sales_by_country_test.rb +18 -3
  362. data/test/queries/workarea/reports/sales_by_product_test.rb +28 -8
  363. data/test/queries/workarea/reports/sales_by_sku_test.rb +28 -8
  364. data/test/queries/workarea/reports/sales_by_tender_test.rb +100 -0
  365. data/test/queries/workarea/reports/sales_by_traffic_referrer_test.rb +6 -6
  366. data/test/queries/workarea/search/admin_releases_test.rb +1 -26
  367. data/test/queries/workarea/search/admin_search_test.rb +0 -10
  368. data/test/queries/workarea/search/admin_users_test.rb +2 -2
  369. data/test/queries/workarea/search/category_browse_test.rb +53 -0
  370. data/test/queries/workarea/search/facet_sorting/size_test.rb +11 -13
  371. data/test/queries/workarea/search/pagination_test.rb +9 -26
  372. data/test/queries/workarea/search/product_entries_test.rb +27 -0
  373. data/test/queries/workarea/search/product_search_test.rb +0 -16
  374. data/test/queries/workarea/search/storefront_search/response_test.rb +26 -0
  375. data/test/queries/workarea/search/storefront_search_test.rb +34 -36
  376. data/test/services/workarea/cancel_order_test.rb +27 -13
  377. data/test/services/workarea/copy_order_test.rb +17 -0
  378. data/test/services/workarea/direct_upload_test.rb +1 -46
  379. data/test/services/workarea/export_report_test.rb +41 -45
  380. data/test/services/workarea/hash_update_test.rb +12 -12
  381. data/test/services/workarea/packaging_test.rb +9 -11
  382. data/test/services/workarea/save_publishing_test.rb +23 -0
  383. data/test/workers/sidekiq/callbacks_test.rb +0 -22
  384. data/test/workers/workarea/deactivate_stale_discounts_test.rb +2 -2
  385. data/test/workers/workarea/index_category_changes_test.rb +5 -7
  386. data/test/workers/workarea/keep_product_index_fresh_test.rb +1 -1
  387. data/test/workers/workarea/process_import_test.rb +0 -6
  388. data/test/workers/workarea/process_search_recommendations_test.rb +4 -5
  389. data/test/workers/workarea/status_reporter_test.rb +2 -1
  390. data/test/workers/workarea/synchronize_user_metrics_test.rb +57 -0
  391. data/test/workers/workarea/update_payment_profile_email_test.rb +27 -0
  392. data/test/workers/workarea/verify_scheduled_releases_test.rb +0 -26
  393. data/workarea-core.gemspec +12 -10
  394. metadata +188 -78
  395. data/app/assets/javascripts/workarea/core/templates/ui_menu_item.jst.ejs +0 -10
  396. data/app/controllers/workarea/admin_guest_browsing.rb +0 -54
  397. data/app/middleware/workarea/rack_cache_config_middleware.rb +0 -19
  398. data/app/queries/workarea/search/search_suggestions.rb +0 -43
  399. data/app/workers/workarea/bust_discount_cache.rb +0 -16
  400. data/app/workers/workarea/clean_user_activity.rb +0 -11
  401. data/app/workers/workarea/undo_release.rb +0 -15
  402. data/app/workers/workarea/update_email.rb +0 -33
  403. data/lib/generators/workarea/docker/USAGE +0 -16
  404. data/lib/generators/workarea/docker/docker_generator.rb +0 -61
  405. data/lib/generators/workarea/docker/templates/.env.erb +0 -6
  406. data/lib/generators/workarea/docker/templates/Dockerfile.erb +0 -48
  407. data/lib/generators/workarea/docker/templates/docker-compose.yml.erb +0 -72
  408. data/lib/generators/workarea/docker/templates/docker-entrypoint.sh.erb +0 -6
  409. data/lib/generators/workarea/docker/templates/docker-sync.yml.erb +0 -8
  410. data/lib/generators/workarea/docker/templates/docker-wait.sh +0 -11
  411. data/lib/generators/workarea/docker/templates/docker.env +0 -16
  412. data/lib/generators/workarea/docker/templates/docker_init.rb.erb +0 -29
  413. data/lib/workarea/configuration/headless_chrome.rb +0 -42
  414. data/lib/workarea/configuration/puma.rb +0 -37
  415. data/lib/workarea/ext/freedom_patches/i18n_js.rb +0 -27
  416. data/lib/workarea/ext/freedom_patches/mongoid_localized_defaults.rb +0 -25
  417. data/lib/workarea/ext/jbuilder/jbuilder_cache.rb +0 -29
  418. data/lib/workarea/ext/referer_parser/parser.decorator +0 -43
  419. data/lib/workarea/queues_pauser.rb +0 -26
  420. data/lib/workarea/robots.rb +0 -9
  421. data/test/generators/workarea/docker_generator_test.rb +0 -156
  422. data/test/javascripts/fixtures/duplicate_id_pass.html.haml +0 -2
  423. data/test/lib/workarea/ext/freedom_patches/mongoid_localized_defaults_test.rb +0 -25
  424. data/test/lib/workarea/ext/referer_parser/parser_test.rb +0 -20
  425. data/test/queries/workarea/search/search_suggestions_test.rb +0 -29
  426. data/test/workers/workarea/undo_release_test.rb +0 -23
  427. data/test/workers/workarea/update_email_test.rb +0 -39
@@ -44,27 +44,22 @@ module Workarea
44
44
 
45
45
  def save(document, options = {})
46
46
  options = options.merge(type: type)
47
- current_index.save(document, options)
47
+ I18n.for_each_locale { current_index.save(document, options) }
48
48
  end
49
49
 
50
- def bulk(documents = [], options = {})
50
+ def bulk(documents, options = {})
51
51
  options = options.merge(type: type)
52
-
53
- if block_given?
54
- I18n.for_each_locale { current_index.bulk(Array.wrap(yield), options) }
55
- else
56
- current_index.bulk(documents, options)
57
- end
52
+ I18n.for_each_locale { current_index.bulk(documents, options) }
58
53
  end
59
54
 
60
55
  def update(document, options = {})
61
56
  options = options.merge(type: type)
62
- current_index.update(document, options)
57
+ I18n.for_each_locale { current_index.update(document, options) }
63
58
  end
64
59
 
65
60
  def delete(id, options = {})
66
61
  options = options.merge(type: type)
67
- current_index.delete(id, options)
62
+ I18n.for_each_locale { current_index.delete(id, options) }
68
63
  end
69
64
 
70
65
  def count(query = nil, options = {})
@@ -102,14 +97,12 @@ module Workarea
102
97
  end
103
98
 
104
99
  def save(options = {})
105
- I18n.for_each_locale do
106
- document = as_document.merge(Serializer.serialize(model))
107
- self.class.save(document, options)
108
- end
100
+ document = as_document.merge(Serializer.serialize(model))
101
+ self.class.save(document, options)
109
102
  end
110
103
 
111
104
  def destroy(options = {})
112
- I18n.for_each_locale { self.class.delete(id, options) }
105
+ self.class.delete(id, options)
113
106
  end
114
107
  end
115
108
  end
@@ -11,13 +11,11 @@ module ActionView
11
11
  end
12
12
 
13
13
  def cache_fragment_name(*)
14
- result = super
15
-
16
- if request.env['workarea.cache_varies'].present?
17
- result << request.env['workarea.cache_varies']
18
- end
14
+ super.tap { |result| result << cache_varies if cache_varies.present? }
15
+ end
19
16
 
20
- result
17
+ def cache_varies
18
+ request.env['workarea.cache_varies']
21
19
  end
22
20
  end
23
21
  end
@@ -0,0 +1,14 @@
1
+ module ActiveSupport
2
+ class Duration
3
+ class << self
4
+ def mongoize(object)
5
+ object.parts.to_a.first.reverse
6
+ end
7
+ alias_method :evolve, :mongoize
8
+
9
+ def demongoize(object)
10
+ object.first.to_i.send(object.last.to_sym)
11
+ end
12
+ end
13
+ end
14
+ end
@@ -1,4 +1,15 @@
1
1
  class Money
2
+ module BlankMongoizing
3
+ def mongoize(value)
4
+ return nil if value.blank?
5
+ super(value)
6
+ end
7
+ end
8
+
9
+ class << self
10
+ prepend BlankMongoizing
11
+ end
12
+
2
13
  alias_method :to_m, :to_money
3
14
 
4
15
  def as_json(*)
@@ -0,0 +1,6 @@
1
+ class Premailer
2
+ def convert_to_text(html, line_length = 65, from_charset = 'UTF-8')
3
+ html.gsub!(/<script.*script>/m, '')
4
+ super(html, line_length, from_charset)
5
+ end
6
+ end
@@ -1,13 +1,28 @@
1
+ # frozen_string_literal: true
2
+
1
3
  class String
4
+ #
5
+ # These two methods are to cut down on object allocation
6
+ #
7
+
8
+ def self.optionize_unwanted_chars_regex
9
+ @optionize_unwanted_chars_regex ||= /[^a-z0-9\-_]+/
10
+ end
11
+
12
+ def self.optionize_seperator_regexes
13
+ @optionize_seperator_regexes ||= {}
14
+ end
15
+
2
16
  def optionize(sep = '-')
3
- result = downcase.strip
17
+ result = downcase
18
+ result.strip!
4
19
 
5
20
  # Turn unwanted chars into the separator
6
- result.gsub!(/[^a-z0-9\-_]+/, sep)
7
- re_sep = Regexp.escape(sep)
21
+ result.gsub!(String.optionize_unwanted_chars_regex, sep)
8
22
 
9
23
  # No more than one of the separator in a row.
10
- result.gsub!(/#{re_sep}{2,}/, sep)
24
+ String.optionize_seperator_regexes[sep] ||= /#{Regexp.escape(sep)}{2,}/
25
+ result.gsub!(String.optionize_seperator_regexes[sep], sep)
11
26
 
12
27
  result.underscore
13
28
  end
@@ -4,8 +4,8 @@ module Mongoid
4
4
  ids = Array(ids).flatten
5
5
  return [] if ids.blank?
6
6
 
7
- unsorted = any_in(id: ids).to_a
8
- ids.map { |id| unsorted.detect { |p| p.id.to_s == id.to_s } }.compact
7
+ lookup = scoped.any_in(id: ids).to_lookup_hash
8
+ ids.map { |id| lookup[id] }.compact
9
9
  end
10
10
  end
11
11
  end
@@ -0,0 +1,30 @@
1
+ module Mongoid
2
+ class LookupHash
3
+ delegate_missing_to :@table
4
+
5
+ def initialize(klass)
6
+ @klass = klass
7
+ @table = {}
8
+ end
9
+
10
+ def [](value)
11
+ @table[value] || @table[@klass.fields['_id'].type.mongoize(value)]
12
+ end
13
+ end
14
+
15
+ class Criteria
16
+ def to_lookup_hash
17
+ scoped.each_with_object(LookupHash.new(klass)) do |model, result|
18
+ result[model.id] = model
19
+ end
20
+ end
21
+
22
+ alias_method :to_lookup_h, :to_lookup_hash
23
+ end
24
+
25
+ module Document
26
+ class_methods do
27
+ delegate :to_lookup_h, :to_lookup_hash, to: :criteria
28
+ end
29
+ end
30
+ end
@@ -8,7 +8,7 @@ module Workarea
8
8
  end
9
9
 
10
10
  def country
11
- Country[
11
+ @country ||= Country[
12
12
  @env['HTTP_GEOIP2_DATA_COUNTRY_CODE'].presence ||
13
13
  @env['HTTP_GEOIP_CITY_COUNTRY_CODE'].presence ||
14
14
  request.try(:country_code)
@@ -16,29 +16,35 @@ module Workarea
16
16
  end
17
17
 
18
18
  def region
19
- region_from_geoip2.presence ||
19
+ @region ||= region_from_geoip2.presence ||
20
20
  @env['HTTP_GEOIP_REGION'].presence ||
21
21
  request_data['region_code']
22
22
  end
23
23
 
24
+ def subdivision
25
+ return @subdivision if defined?(@subdivision)
26
+ @subdivision = country&.subdivisions&.fetch(region) rescue nil
27
+ end
28
+
24
29
  def city
25
- @env['HTTP_GEOIP2_DATA_CITY_NAME'].presence ||
30
+ @city ||= @env['HTTP_GEOIP2_DATA_CITY_NAME'].presence ||
26
31
  @env['HTTP_GEOIP_CITY'].presence ||
27
32
  request.try(:city)
28
33
  end
29
34
 
30
35
  def postal_code
31
- @env['HTTP_GEOIP_POSTAL_CODE'].presence || request.try(:postal_code)
36
+ @postal_code ||= @env['HTTP_GEOIP_POSTAL_CODE'].presence ||
37
+ request.try(:postal_code)
32
38
  end
33
39
 
34
40
  def latitude
35
- @env['HTTP_GEOIP2_DATA_LATITUDE'].presence ||
41
+ @latitude ||= @env['HTTP_GEOIP2_DATA_LATITUDE'].presence ||
36
42
  @env['HTTP_GEOIP_LATITUDE'].presence ||
37
43
  request.try(:latitude)
38
44
  end
39
45
 
40
46
  def longitude
41
- @env['HTTP_GEOIP2_DATA_LONGITUDE'].presence ||
47
+ @longitude ||= @env['HTTP_GEOIP2_DATA_LONGITUDE'].presence ||
42
48
  @env['HTTP_GEOIP_LONGITUDE'].presence ||
43
49
  request.try(:longitude)
44
50
  end
@@ -50,6 +56,18 @@ module Workarea
50
56
  [latitude, longitude]
51
57
  end
52
58
 
59
+ def names
60
+ @names ||= [
61
+ postal_code,
62
+ city,
63
+ region,
64
+ subdivision&.name,
65
+ country&.alpha2,
66
+ country&.alpha3,
67
+ country&.name
68
+ ].reject(&:blank?)
69
+ end
70
+
53
71
  private
54
72
 
55
73
  def request
@@ -2,7 +2,7 @@ module Workarea
2
2
  module RoutesConstraints
3
3
  class SuperAdmin
4
4
  def matches?(request)
5
- user_id = request.cookie_jar.signed[:user_id]
5
+ user_id = request.session[:user_id]
6
6
  return false if user_id.blank?
7
7
  User.find(user_id).super_admin?
8
8
  end
@@ -1,10 +1,9 @@
1
1
  module Workarea
2
2
  module VERSION
3
3
  MAJOR = 3
4
- MINOR = 4
5
- PATCH = 44
6
- PRE = nil
7
-
4
+ MINOR = 5
5
+ PATCH = 0
6
+ PRE = 'beta.1'
8
7
  STRING = [MAJOR, MINOR, PATCH, PRE].compact.join('.')
9
8
 
10
9
  module MONGODB
@@ -0,0 +1,92 @@
1
+ module Workarea
2
+ class Visit
3
+ class UnsupportedSessionAccess < RuntimeError; end
4
+
5
+ attr_reader :env
6
+ attr_writer :override_segments
7
+
8
+ delegate :postal_code, :city, :subdivision, :region, :country, to: :geolocation
9
+ delegate :admin?, to: :metrics
10
+
11
+ def initialize(env)
12
+ @env = env
13
+ end
14
+
15
+ def cookies
16
+ request.cookie_jar
17
+ end
18
+
19
+ def session
20
+ raise UnsupportedSessionAccess unless Configuration::Session.cookie_store?
21
+ @session ||= (cookies.signed_or_encrypted[Configuration::Session.key] || {}).with_indifferent_access
22
+ end
23
+
24
+ def logged_in?
25
+ session[:user_id].present?
26
+ end
27
+
28
+ def request
29
+ @request ||= ActionDispatch::Request.new(env)
30
+ end
31
+
32
+ def geolocation
33
+ @geolocation ||= Workarea::Geolocation.new(env, request.remote_ip)
34
+ end
35
+
36
+ def location_names
37
+ geolocation.names
38
+ end
39
+
40
+ def current_email
41
+ cookies.signed[:email]
42
+ end
43
+
44
+ def metrics
45
+ return blank_metrics if current_metrics_id.blank?
46
+ @metrics ||= Metrics::User.find_or_initialize_by(id: current_metrics_id)
47
+ end
48
+
49
+ # A value of 0 here means it's the first request we've seen
50
+ def sessions
51
+ @sessions ||= cookies[:sessions].to_i
52
+ end
53
+
54
+ def segments
55
+ @segments ||= Segment.find_qualifying(self)
56
+ end
57
+
58
+ def override_segments
59
+ @override_segments ||= Segment.in(id: session[:segment_ids]).to_a
60
+ end
61
+
62
+ def applied_segments
63
+ admin? ? override_segments : segments
64
+ end
65
+
66
+ def referrer
67
+ return @referrer if defined?(@referrer)
68
+ @referrer = Workarea.referrer_parser.parse(request.referrer) rescue {}
69
+ end
70
+
71
+ def browser
72
+ @browser ||= Browser.new(env['HTTP_USER_AGENT'], accept_language: env['HTTP_ACCEPT_LANGUAGE'])
73
+ end
74
+
75
+ def current_metrics_id
76
+ return @current_metrics_id if defined?(@current_metrics_id)
77
+ @current_metrics_id = current_email.presence || session['session_id']
78
+ end
79
+
80
+ def current_metrics_id=(id)
81
+ @current_metrics_id = id
82
+ @metrics = nil
83
+ end
84
+
85
+ private
86
+
87
+ # Memoizing this saves a lot of allocated objects
88
+ def blank_metrics
89
+ @blank_metrics ||= Metrics::User.new
90
+ end
91
+ end
92
+ end
@@ -0,0 +1,95 @@
1
+ module Workarea
2
+ module Warnings
3
+ extend self
4
+
5
+ def check
6
+ check_timezone
7
+ check_mongo_notable_scan
8
+ check_dragonfly_config
9
+ check_auto_capture
10
+ end
11
+
12
+ def check_timezone
13
+ if Rails.application.config.time_zone == 'UTC'
14
+ warn <<~eos
15
+ **************************************************
16
+ ⛔️ WARNING: Rails.application.config.time_zone is set to UTC, which you \
17
+ probably don't want.
18
+ As of Workarea 3.2, we use that value as the standard \
19
+ timezone for the admin side of the application.
20
+ We recommend setting this to the timezone of the retailer. Contact them to \
21
+ find their preference.
22
+ **************************************************
23
+ eos
24
+ end
25
+ end
26
+
27
+ def check_mongo_notable_scan
28
+ if (Rails.env.development? &&
29
+ !Workarea.config.skip_service_connections &&
30
+ Configuration::Mongoid.indexes_enforced?)
31
+ warn <<~eos
32
+ **************************************************
33
+ ⛔️ WARNING: MongoDB is configured with notablescan.
34
+
35
+ This means that MongoDB won't run queries that require a collection scan and will return an error.
36
+ Workarea turns this on for running tests to assert that queries have indexes, and turns it off at the end of the test run.
37
+ Since you're not running in the test environment and this is turned on, it might mean the test process was killed, preventing Workarea from turning it off.
38
+
39
+ To turn this off, start the mongo shell and run this command:
40
+ db.getSiblingDB("admin").runCommand( { setParameter: 1, notablescan: 0 } )
41
+ **************************************************
42
+ eos
43
+ end
44
+ end
45
+
46
+ def check_dragonfly_config
47
+ if !Rails.env.test? && !Rails.env.development? &&
48
+ Dragonfly.app(:workarea).datastore.is_a?(Dragonfly::FileDataStore)
49
+
50
+ warn <<~eos
51
+ **************************************************
52
+ ⛔️ WARNING: Dragonfly is configured to use the filesystem.
53
+
54
+ This means all dragonfly assets (assets, product images, etc.) will be stored
55
+ locally and not accessible to all servers within your environment.
56
+
57
+ We recommend using S3 when running in a live environment by setting
58
+ WORKAREA_S3_REGION and WORKAREA_S3_BUCKET_NAME in your environment variables.
59
+ Workarea will automatically configure Dragonfly to use S3 if those values
60
+ are present.
61
+ **************************************************
62
+ eos
63
+ end
64
+ end
65
+
66
+ def check_auto_capture
67
+ if Workarea.config.auto_capture
68
+ warn <<~eos
69
+ **************************************************
70
+ ⛔️ WARNING: Workarea is configured with Workarea.config.auto_capture.
71
+
72
+ In v3.5, this is being deprecated to allow more flexibility based on the types
73
+ of items in the order.
74
+
75
+ You should set Workarea.config.checkout_payment_action instead. You can set it
76
+ for each type of order, here are the defaults:
77
+ {
78
+ shipped: 'authorize!',
79
+ not_shipped: 'purchase!',
80
+ mixed: 'authorize!'
81
+ }
82
+
83
+ To achieve the same functionality as Workarea.config.auto_capture, you'd set:
84
+ {
85
+ shipped: 'purchase!',
86
+ not_shipped: 'purchase!',
87
+ mixed: 'purchase!'
88
+ }
89
+
90
+ **************************************************
91
+ eos
92
+ end
93
+ end
94
+ end
95
+ end