workarea-registries 1.0.0

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 (100) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +22 -0
  3. data/Gemfile +9 -0
  4. data/LICENSE +21 -0
  5. data/README.md +1 -0
  6. data/Rakefile +58 -0
  7. data/app/assets/images/workarea/storefront/registries/icons/email.svg +4 -0
  8. data/app/assets/images/workarea/storefront/registries/icons/link.svg +1 -0
  9. data/app/assets/javascripts/workarea/storefront/registries/modules/add_to_registry_button.js +49 -0
  10. data/app/assets/javascripts/workarea/storefront/registries/modules/copy_registry_url_button.js +51 -0
  11. data/app/assets/javascripts/workarea/storefront/registries/modules/toggle_registry_address.js +58 -0
  12. data/app/assets/javascripts/workarea/storefront/registries/templates/add_to_registry_button.jst.ejs +3 -0
  13. data/app/controllers/workarea/admin/registries_controller.rb +28 -0
  14. data/app/controllers/workarea/storefront/cart_items_controller.decorator +14 -0
  15. data/app/controllers/workarea/storefront/registries_controller.rb +47 -0
  16. data/app/controllers/workarea/storefront/users/registries_controller.rb +94 -0
  17. data/app/controllers/workarea/storefront/users/registry_items_controller.rb +67 -0
  18. data/app/controllers/workarea/storefront/users/registry_shares_controller.rb +43 -0
  19. data/app/controllers/workarea/storefront/users/registry_thanks_controller.rb +41 -0
  20. data/app/helpers/workarea/registries_helper.rb +41 -0
  21. data/app/mailers/workarea/storefront/registries_mailer.rb +52 -0
  22. data/app/models/workarea/checkout/steps/addresses.decorator +28 -0
  23. data/app/models/workarea/order.decorator +7 -0
  24. data/app/models/workarea/order/item.decorator +11 -0
  25. data/app/models/workarea/registry.rb +129 -0
  26. data/app/models/workarea/registry/item.rb +39 -0
  27. data/app/models/workarea/registry/public_search.rb +23 -0
  28. data/app/models/workarea/registry/share.rb +46 -0
  29. data/app/models/workarea/registry/thank.rb +26 -0
  30. data/app/models/workarea/search/admin/registry.rb +29 -0
  31. data/app/queries/workarea/search/admin_orders.decorator +7 -0
  32. data/app/queries/workarea/search/admin_registries.rb +16 -0
  33. data/app/seeds/workarea/registry_content_seeds.rb +50 -0
  34. data/app/services/workarea/inventory_adjustment.decorator +43 -0
  35. data/app/view_models/workarea/admin/registry_view_model.rb +19 -0
  36. data/app/view_models/workarea/storefront/checkout/addresses_view_model.decorator +17 -0
  37. data/app/view_models/workarea/storefront/order_item_view_model.decorator +9 -0
  38. data/app/view_models/workarea/storefront/order_view_model.decorator +8 -0
  39. data/app/view_models/workarea/storefront/registry_email_view_model.rb +37 -0
  40. data/app/view_models/workarea/storefront/registry_item_view_model.rb +72 -0
  41. data/app/view_models/workarea/storefront/registry_share_view_model.rb +6 -0
  42. data/app/view_models/workarea/storefront/registry_thank_view_model.rb +6 -0
  43. data/app/view_models/workarea/storefront/registry_view_model.rb +74 -0
  44. data/app/view_models/workarea/storefront/user_view_model.decorator +12 -0
  45. data/app/views/workarea/admin/registries/_menu.html.haml +1 -0
  46. data/app/views/workarea/admin/registries/index.html.haml +70 -0
  47. data/app/views/workarea/storefront/carts/_registry_details.html.haml +3 -0
  48. data/app/views/workarea/storefront/checkouts/_registry_address.html.haml +13 -0
  49. data/app/views/workarea/storefront/checkouts/_registry_address_fields.html.haml +28 -0
  50. data/app/views/workarea/storefront/checkouts/_registry_details.html.haml +3 -0
  51. data/app/views/workarea/storefront/products/_add_to_registry_placeholder.html.haml +1 -0
  52. data/app/views/workarea/storefront/registries/_registries_link.html.haml +4 -0
  53. data/app/views/workarea/storefront/registries/index.html.haml +39 -0
  54. data/app/views/workarea/storefront/registries/search.html.haml +35 -0
  55. data/app/views/workarea/storefront/registries/show.html.haml +63 -0
  56. data/app/views/workarea/storefront/registries_mailer/creation.html.haml +13 -0
  57. data/app/views/workarea/storefront/registries_mailer/gift_receipt.html.haml +51 -0
  58. data/app/views/workarea/storefront/registries_mailer/share.html.haml +21 -0
  59. data/app/views/workarea/storefront/registries_mailer/thank.html.haml +19 -0
  60. data/app/views/workarea/storefront/users/_registry_count.json.jbuilder +3 -0
  61. data/app/views/workarea/storefront/users/accounts/_registries.html.haml +14 -0
  62. data/app/views/workarea/storefront/users/registries/_form.html.haml +56 -0
  63. data/app/views/workarea/storefront/users/registries/_radio_list.html.haml +8 -0
  64. data/app/views/workarea/storefront/users/registries/_summary.html.haml +12 -0
  65. data/app/views/workarea/storefront/users/registries/edit.html.haml +4 -0
  66. data/app/views/workarea/storefront/users/registries/index.html.haml +24 -0
  67. data/app/views/workarea/storefront/users/registries/new.html.haml +4 -0
  68. data/app/views/workarea/storefront/users/registries/show.html.haml +75 -0
  69. data/app/views/workarea/storefront/users/registry_items/new.html.haml +10 -0
  70. data/app/views/workarea/storefront/users/registry_items/templates/_purchased.html.haml +29 -0
  71. data/app/views/workarea/storefront/users/registry_items/templates/_unpurchased.html.haml +35 -0
  72. data/app/views/workarea/storefront/users/registry_shares/_share_buttons.html.haml +18 -0
  73. data/app/views/workarea/storefront/users/registry_shares/new.html.haml +49 -0
  74. data/app/views/workarea/storefront/users/registry_thanks/new.html.haml +47 -0
  75. data/app/workers/workarea/send_gift_receipt.rb +15 -0
  76. data/app/workers/workarea/send_registry_creation_email.rb +12 -0
  77. data/app/workers/workarea/update_registry_items.rb +24 -0
  78. data/bin/rails +20 -0
  79. data/config/initializers/appends.rb +54 -0
  80. data/config/initializers/fields.rb +19 -0
  81. data/config/locales/en.yml +133 -0
  82. data/config/routes.rb +26 -0
  83. data/lib/workarea/mailer_previews/storefront/registry_mailer_preview.rb +25 -0
  84. data/lib/workarea/registries.rb +11 -0
  85. data/lib/workarea/registries/engine.rb +17 -0
  86. data/lib/workarea/registries/version.rb +5 -0
  87. data/test/dummy/config/application.rb +27 -0
  88. data/test/factories/workarea/registry.rb +67 -0
  89. data/test/integration/workarea/storefront/cart_item_registry_integration_test.rb +104 -0
  90. data/test/integration/workarea/storefront/checkout_registry_integration_test.rb +156 -0
  91. data/test/integration/workarea/storefront/registry_privacy_integration_test.rb +48 -0
  92. data/test/integration/workarea/storefront/user_registries_integration_test.rb +50 -0
  93. data/test/integration/workarea/storefront/user_registry_items_integration_test.rb +106 -0
  94. data/test/models/workarea/registry/item_test.rb +22 -0
  95. data/test/models/workarea/registry/public_search_test.rb +48 -0
  96. data/test/models/workarea/registry_test.rb +113 -0
  97. data/test/system/workarea/admin/registry_system_test.rb +20 -0
  98. data/test/workers/update_registry_items_test.rb +45 -0
  99. data/workarea-registries.gemspec +20 -0
  100. metadata +156 -0
@@ -0,0 +1,19 @@
1
+ Workarea::Configuration.define_fields do
2
+ fieldset 'Communication', namespaced: false do
3
+ field 'Max Email Registry Share Message Length',
4
+ type: :integer,
5
+ default: 2000,
6
+ description: %(
7
+ The maximum message length (in characters) that an email share
8
+ can contain. Used in the 'Share by Email' option on registry detail pages.
9
+ ).squish
10
+
11
+ field 'Max Email Registry Thanks Message Length',
12
+ type: :integer,
13
+ default: 2000,
14
+ description: %(
15
+ The maximum message length (in characters) that an email share
16
+ can contain. Used in the 'Thank You' option on registry detail pages.
17
+ ).squish
18
+ end
19
+ end
@@ -0,0 +1,133 @@
1
+ en:
2
+ workarea:
3
+ admin:
4
+ registries:
5
+ index:
6
+ dashboard_link: Orders dashboard
7
+ page_title: Registries
8
+ title: Registries
9
+ pluralize:
10
+ one: '%{count} Registry'
11
+ other: '%{count} Registries'
12
+ errors:
13
+ messages:
14
+ registry_sku_unavailable: "Sorry, %{registry} is not asking for %{sku} anymore. It has been removed"
15
+ registry_sku_limited_quantity: "%{registry} is only asking for %{quantity} of %{sku}, your quantity has been adjusted"
16
+ storefront:
17
+ carts:
18
+ registry_item: Registry Item
19
+ checkouts:
20
+ ship_to_another_address: Ship order to specified address
21
+ ship_to_registrant: Ship order to registrant's address
22
+ email:
23
+ registries:
24
+ creation:
25
+ heading: "%{registry_name}"
26
+ subject: You have created a new registry!
27
+ share:
28
+ from_info: Click the link below to view my registry.
29
+ subject: A Message from %{from}
30
+ gift_receipt:
31
+ heading: "Gift Receipt for Order: %{order_id}"
32
+ subject: Items have been purchased for your registry.
33
+ thank:
34
+ from_info: 'has included a personal note:'
35
+ subject: Thank you from %{from}
36
+ thank_you: wants to thank you for your gift!
37
+ flash_messages:
38
+ private_registry: This registry is private.
39
+ registry_created: Your registry has been created.
40
+ registry_item_created: Item has been added to your registry.
41
+ registry_item_destroyed: Item has been removed.
42
+ registry_item_not_created: Item could not be added to your registry.
43
+ registry_item_not_destroyed: Purchased items cannot be removed from your registry.
44
+ registry_item_updated: Item has been updated.
45
+ registry_not_created: There was a problem creating your registry.
46
+ registry_updated: Registry has been updated.
47
+ registry_item_not_updated: Item failed to update.
48
+ registry_not_updated: Registry could not been updated.
49
+ registry_share_message_sent: Thanks for sharing! An email has been sent to %{recipient}.
50
+ registry_thank_message_sent: An email has been sent to %{recipient}.
51
+ registry_url_copied: Link to Registry has been Copied!
52
+ registry_url_not_copied: "Something went wrong: %{error}"
53
+ products:
54
+ add_to_registry: Add to Registry
55
+ registries:
56
+ create: Add a Registry
57
+ description: Description
58
+ edit: Edit
59
+ edit_title: Edit %{name}
60
+ email: Email
61
+ event_date: Event Date
62
+ filter: Filter
63
+ index:
64
+ create: Easily create a registry and start adding products!
65
+ create_link: Create
66
+ find: Search for a registry by name or registry number.
67
+ find_link: Find
68
+ manage: Make changes or update an existing registry
69
+ manage_link: Manage
70
+ issues:
71
+ no_items: Your registry contains no items!
72
+ nothing_to_purchase: All items on this registry have been purchased!
73
+ items: Items
74
+ name: Registry Name
75
+ name_or_email: Search by Registry Name or Email
76
+ new: Create Your Registry
77
+ none: You haven't added a registry yet.
78
+ no_event_date: No date selected.
79
+ privacy_settings: Privacy Settings
80
+ private_privacy: Private
81
+ public_privacy: Public
82
+ purchased_items: Purchased Items
83
+ registry_home: Registry Home
84
+ registry_label: "%{name}'s Registry Item"
85
+ registry_search: Registry Search
86
+ registries_link: Registries
87
+ requested: '%{quantity} requested'
88
+ shared_privacy: Shared
89
+ share: Share your Registry
90
+ shipping_address: Shipping Address
91
+ show: Show
92
+ show_title: "%{name}'s Registry"
93
+ search:
94
+ heading: Search Registries
95
+ search_title: Registry Search
96
+ title: Registries
97
+ quantity_purchased: '%{quantity} purchased'
98
+ unpurchased_items: Unpurchased Items
99
+ view: View
100
+ view_all: View all your registries
101
+ your_registries: Your Registries
102
+ registry:
103
+ item:
104
+ purchased: purchased
105
+ thank_you: Say Thanks
106
+ unpurchased: unpurchased
107
+ deletion_confirm: Are you sure?
108
+ share:
109
+ copy_link: Copy link to clipboard
110
+ email: Email
111
+ from: From
112
+ from_email_placeholder: Your Email
113
+ from_name_placeholder: Your Name
114
+ message: Message
115
+ message_placeholder: Add a personal message
116
+ name: Name
117
+ share_title: Share by Email
118
+ share_by_email: Share by Email
119
+ to: To
120
+ to_email_placeholder: Friend's Email
121
+ to_name_placeholder: Friend's Name
122
+ thank:
123
+ email: Email
124
+ from: From
125
+ from_email_placeholder: Your Email
126
+ from_name_placeholder: Your Name
127
+ message: Message
128
+ message_placeholder: Add a personal message
129
+ name: Name
130
+ thank_you_email: Say Thanks
131
+ to: To
132
+ to_email_placeholder: Friend's Email
133
+ to_name_placeholder: Friend's Name
data/config/routes.rb ADDED
@@ -0,0 +1,26 @@
1
+ Workarea::Storefront::Engine.routes.draw do
2
+ scope '(:locale)', constraints: Workarea::I18n.routes_constraint do
3
+ namespace :users do
4
+ resources :registries do
5
+
6
+ collection do
7
+ resources :items, only: [:new, :create], as: :registry_items, controller: :registry_items
8
+ resources :shares, only: [:new, :create], as: :registry_shares, controller: :registry_shares
9
+ resources :thanks, only: [:new, :create], as: :registry_thanks, controller: :registry_thanks
10
+ end
11
+
12
+ resources :items, only: [:update, :destroy], controller: :registry_items
13
+ end
14
+ end
15
+
16
+ resources :registries, only: [:show, :index]
17
+
18
+ get 'registry/search', to: 'registries#search'
19
+ end
20
+ end
21
+
22
+ Workarea::Admin::Engine.routes.draw do
23
+ scope '(:locale)', constraints: Workarea::I18n.routes_constraint do
24
+ resources :registries, only: [:index, :show]
25
+ end
26
+ end
@@ -0,0 +1,25 @@
1
+ module Workarea
2
+ module Storefront
3
+ class RegistriesMailerPreview < ActionMailer::Preview
4
+ def creation
5
+ registry = Registry.first
6
+ RegistriesMailer.creation(registry.id)
7
+ end
8
+
9
+ def share
10
+ share = Registry::Share.first
11
+ RegistriesMailer.share(share.id)
12
+ end
13
+
14
+ def thank
15
+ thank = Registry::Thank.first
16
+ RegistriesMailer.thank(thank.id)
17
+ end
18
+
19
+ def gift_receipt
20
+ order = Order.where(ship_to_registrant: true).first
21
+ RegistriesMailer.gift_receipt(order.id)
22
+ end
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,11 @@
1
+ require 'workarea'
2
+ require 'workarea/storefront'
3
+ require 'workarea/admin'
4
+
5
+ require 'workarea/registries/engine'
6
+ require 'workarea/registries/version'
7
+
8
+ module Workarea
9
+ module Registries
10
+ end
11
+ end
@@ -0,0 +1,17 @@
1
+ module Workarea
2
+ module Registries
3
+ class Engine < ::Rails::Engine
4
+ include Workarea::Plugin
5
+ isolate_namespace Workarea::Registries
6
+
7
+ config.to_prepare do
8
+ Workarea::ApplicationController.helper(Workarea::RegistriesHelper)
9
+ Workarea::ApplicationMailer.helper(Workarea::RegistriesHelper)
10
+
11
+ # Shouldn't be necessary, but it seems to be.
12
+ Workarea::Storefront::ApplicationController.helper(Workarea::RegistriesHelper)
13
+ Workarea::Admin::ApplicationController.helper(Workarea::RegistriesHelper)
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,5 @@
1
+ module Workarea
2
+ module Registries
3
+ VERSION = '1.0.0'.freeze
4
+ end
5
+ end
@@ -0,0 +1,27 @@
1
+ require_relative 'boot'
2
+
3
+ require 'action_controller/railtie'
4
+ require 'action_view/railtie'
5
+ require 'action_mailer/railtie'
6
+ require 'rails/test_unit/railtie'
7
+ require 'sprockets/railtie'
8
+ require 'teaspoon-mocha'
9
+
10
+ # Workarea must be required before other gems to ensure control over Rails.env
11
+ # for running tests
12
+ require 'workarea/core'
13
+ require 'workarea/admin'
14
+ require 'workarea/storefront'
15
+ Bundler.require(*Rails.groups)
16
+ require 'workarea/registries'
17
+
18
+ module Dummy
19
+ class Application < Rails::Application
20
+ # Initialize configuration defaults for originally generated Rails version.
21
+ config.load_defaults 5.1
22
+
23
+ # Settings in config/environments/* take precedence over those specified here.
24
+ # Application configuration should go into files in config/initializers
25
+ # -- all .rb files in that directory are automatically loaded.
26
+ end
27
+ end
@@ -0,0 +1,67 @@
1
+ module Workarea
2
+ module Factories
3
+ module Registry
4
+ Factories.add(self)
5
+
6
+ def create_registry(overrides = {})
7
+ attributes = {
8
+ name: 'Test Registry',
9
+ }.merge(overrides)
10
+
11
+ attributes[:user_id] = create_user.id if attributes[:user_id].nil?
12
+ attributes[:email] = create_user.email if attributes[:email].nil?
13
+ Workarea::Registry.create!(attributes)
14
+ end
15
+
16
+ def create_registry_item(registry: nil, **overrides)
17
+ registry ||= create_registry
18
+ attributes = { quantity: 2 }.merge(overrides)
19
+
20
+ if attributes[:product_id].nil?
21
+ product = create_product
22
+ attributes[:product_id] = product.id
23
+ attributes[:sku] = product.variants.first.sku
24
+ end
25
+
26
+ registry.items.create!(attributes)
27
+ end
28
+
29
+ def create_checkout_with_registry_item
30
+ create_tax_category(
31
+ name: 'Sales Tax',
32
+ code: '001',
33
+ rates: [{ percentage: 0.07, country: 'US', region: 'PA' }]
34
+ )
35
+
36
+ registry = create_registry
37
+
38
+ product = create_product(
39
+ variants: [{ sku: 'SKU1', regular: 6.to_m, tax_code: '001' }]
40
+ )
41
+
42
+ registry_item = create_registry_item({
43
+ registry: registry,
44
+ product_id: product.id,
45
+ sku: product.variants.first.sku,
46
+ quantity: 2
47
+ })
48
+
49
+ create_shipping_service(
50
+ carrier: 'UPS',
51
+ name: 'Ground',
52
+ service_code: '03',
53
+ tax_code: '001',
54
+ rates: [{ price: 7.to_m }]
55
+ )
56
+
57
+ post storefront.cart_items_path,
58
+ params: {
59
+ product_id: product.id,
60
+ sku: product.skus.first,
61
+ quantity: 2,
62
+ registry_id: registry.id
63
+ }
64
+ end
65
+ end
66
+ end
67
+ end
@@ -0,0 +1,104 @@
1
+ require 'test_helper'
2
+
3
+ module Workarea
4
+ module Storefront
5
+ class CartItemRegistryIntegrationTest < Workarea::IntegrationTest
6
+ setup :registry, :product
7
+
8
+ def registry
9
+ @registry ||= create_registry
10
+ end
11
+
12
+ def product
13
+ @product ||= create_product(
14
+ name: 'Integration Product',
15
+ variants: [
16
+ { sku: 'SKU1', regular: 5.to_m },
17
+ { sku: 'SKU2', regular: 6.to_m }
18
+ ]
19
+ )
20
+ end
21
+
22
+ def order
23
+ Order.first
24
+ end
25
+
26
+ def test_create_item_from_registry
27
+ registry_item = create_registry_item({
28
+ registry: registry,
29
+ product_id: product.id,
30
+ sku: product.variants.first.sku
31
+ })
32
+
33
+ post storefront.cart_items_path,
34
+ params: {
35
+ product_id: registry_item.product_id,
36
+ sku: registry_item.sku,
37
+ quantity: 1,
38
+ registry_id: registry.id
39
+ }
40
+
41
+ assert(response.ok?)
42
+
43
+ order.reload
44
+ assert_equal(@product.id, order.items.first.product_id)
45
+ assert_equal(@product.skus.first, order.items.first.sku)
46
+ assert_equal(1, order.items.first.quantity)
47
+ assert_equal(5.to_m, order.items.first.total_price)
48
+ assert_equal(@registry.id.to_s, order.items.first.registry_id)
49
+ end
50
+
51
+ def test_cannot_create_more_items_than_requested
52
+ registry_item = create_registry_item({
53
+ registry: registry,
54
+ product_id: product.id,
55
+ sku: product.variants.first.sku,
56
+ received: 1
57
+ })
58
+
59
+ post storefront.cart_items_path,
60
+ params: {
61
+ product_id: registry_item.product_id,
62
+ sku: registry_item.sku,
63
+ quantity: 2,
64
+ registry_id: @registry.id
65
+ }
66
+
67
+ assert(response.ok?)
68
+
69
+ order.reload
70
+ assert_equal(@product.id, order.items.first.product_id)
71
+ assert_equal(@product.skus.first, order.items.first.sku)
72
+ assert_equal(1, order.items.first.quantity)
73
+ assert_equal(5.to_m, order.items.first.total_price)
74
+ assert_equal(@registry.id.to_s, order.items.first.registry_id)
75
+ end
76
+
77
+ def test_cannot_add_more_quantity_than_requested
78
+ registry_item = create_registry_item({
79
+ registry: registry,
80
+ product_id: product.id,
81
+ sku: product.variants.first.sku,
82
+ received: 1
83
+ })
84
+
85
+ post storefront.cart_items_path,
86
+ params: {
87
+ product_id: registry_item.product_id,
88
+ sku: registry_item.sku,
89
+ quantity: 2,
90
+ registry_id: @registry.id
91
+ }
92
+
93
+ assert(response.ok?)
94
+
95
+ order.reload
96
+ assert_equal(product.id, order.items.first.product_id)
97
+ assert_equal(product.skus.first, order.items.first.sku)
98
+ assert_equal(1, order.items.first.quantity)
99
+ assert_equal(5.to_m, order.items.first.total_price)
100
+ assert_equal(registry.id.to_s, order.items.first.registry_id)
101
+ end
102
+ end
103
+ end
104
+ end