solidus_subscriptions-alpha 0.0.4 → 0.0.5

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 +4 -4
  2. data/LICENSE +26 -26
  3. data/README.md +130 -130
  4. data/Rakefile +28 -28
  5. data/app/assets/javascripts/spree/backend/solidus_subscriptions.js +1 -1
  6. data/app/assets/javascripts/spree/frontend/solidus_subscriptions.js +1 -1
  7. data/app/assets/stylesheets/spree/backend/solidus_subscriptions.css +4 -4
  8. data/app/assets/stylesheets/spree/frontend/solidus_subscriptions.css +4 -4
  9. data/app/controllers/solidus_subscriptions/api/v1/line_items_controller.rb +35 -35
  10. data/app/controllers/solidus_subscriptions/api/v1/subscriptions_controller.rb +44 -44
  11. data/app/controllers/spree/admin/subscriptions_controller.rb +66 -66
  12. data/app/decorators/spree/controllers/api/line_items/create_subscription_line_items.rb +28 -28
  13. data/app/decorators/spree/controllers/orders/create_subscription_line_items.rb +33 -33
  14. data/app/decorators/spree/line_items/subscription_line_items_association.rb +22 -22
  15. data/app/decorators/spree/orders/after_create.rb +15 -15
  16. data/app/decorators/spree/orders/finalize_creates_subscriptions.rb +19 -19
  17. data/app/decorators/spree/orders/subscription_line_items_association.rb +15 -15
  18. data/app/decorators/spree/products/subscribable_decorator.rb +11 -11
  19. data/app/decorators/spree/users/have_many_subscriptions.rb +18 -18
  20. data/app/decorators/spree/variant_pretty_name.rb +13 -13
  21. data/app/jobs/solidus_subscriptions/process_installments_job.rb +22 -22
  22. data/app/models/solidus_subscriptions/checkout.rb +141 -141
  23. data/app/models/solidus_subscriptions/dispatcher.rb +32 -32
  24. data/app/models/solidus_subscriptions/failure_dispatcher.rb +19 -19
  25. data/app/models/solidus_subscriptions/installment.rb +126 -126
  26. data/app/models/solidus_subscriptions/installment_detail.rb +23 -23
  27. data/app/models/solidus_subscriptions/interval.rb +24 -24
  28. data/app/models/solidus_subscriptions/line_item.rb +98 -98
  29. data/app/models/solidus_subscriptions/line_item_builder.rb +44 -44
  30. data/app/models/solidus_subscriptions/order_builder.rb +40 -40
  31. data/app/models/solidus_subscriptions/out_of_stock_dispatcher.rb +19 -19
  32. data/app/models/solidus_subscriptions/payment_failed_dispatcher.rb +23 -23
  33. data/app/models/solidus_subscriptions/subscription.rb +217 -217
  34. data/app/models/solidus_subscriptions/subscription_generator.rb +60 -60
  35. data/app/models/solidus_subscriptions/subscription_line_item_builder.rb +21 -21
  36. data/app/models/solidus_subscriptions/subscription_order_promotion_rule.rb +25 -25
  37. data/app/models/solidus_subscriptions/subscription_promotion_rule.rb +38 -38
  38. data/app/models/solidus_subscriptions/success_dispatcher.rb +16 -16
  39. data/app/models/solidus_subscriptions/unsubscribable_error.rb +17 -17
  40. data/app/models/solidus_subscriptions/user_mismatch_error.rb +15 -15
  41. data/app/overrides/views/admin_subscribable_checkbox.rb +13 -13
  42. data/app/overrides/views/admin_subscriptions_menu_link.rb +8 -8
  43. data/app/overrides/views/subscription_line_item_fields.rb +6 -6
  44. data/app/views/spree/admin/products/_subscribable_checkbox.html.erb +8 -8
  45. data/app/views/spree/admin/promotions/rules/_subscription_order_promotion_rule.html.erb +0 -0
  46. data/app/views/spree/admin/promotions/rules/_subscription_promotion_rule.html.erb +0 -0
  47. data/app/views/spree/admin/shared/_no_objects_found.html.erb +4 -4
  48. data/app/views/spree/admin/shared/_subscription_tab.html.erb +3 -3
  49. data/app/views/spree/admin/solidus_subscriptions/subscriptions/_subscription.html.erb +66 -66
  50. data/app/views/spree/admin/subscriptions/_form.html.erb +81 -81
  51. data/app/views/spree/admin/subscriptions/_legacy_form.html.erb +81 -81
  52. data/app/views/spree/admin/subscriptions/_legacy_sidebar.html.erb +28 -28
  53. data/app/views/spree/admin/subscriptions/edit.html.erb +21 -21
  54. data/app/views/spree/admin/subscriptions/index.html.erb +119 -119
  55. data/app/views/spree/admin/subscriptions/new.html.erb +9 -9
  56. data/app/views/spree/admin/variants/_subscribable_checkbox.html.erb +6 -6
  57. data/app/views/spree/frontend/products/_subscription_line_item_fields.html.erb +30 -30
  58. data/config/locales/en.yml +91 -91
  59. data/config/routes.rb +25 -25
  60. data/db/migrate/20160825164850_create_solidus_subscriptions_subscriptions.rb +11 -11
  61. data/db/migrate/20160825173548_create_solidus_subscriptions_line_items.rb +17 -17
  62. data/db/migrate/20160825202248_create_solidus_subscriptions_installments.rb +23 -23
  63. data/db/migrate/20160825211202_create_solidus_subscriptions_installment_details.rb +22 -22
  64. data/db/migrate/20160825214240_add_subscribable_to_spree_variants.rb +5 -5
  65. data/db/migrate/20160829201653_change_subscription_line_items_installments_to_max_installments.rb +5 -5
  66. data/db/migrate/20160902220242_remove_state_from_solidus_susbscriptions_installment_details.rb +5 -5
  67. data/db/migrate/20160902220604_add_successful_to_solidus_subscriptions_installment_details.rb +5 -5
  68. data/db/migrate/20160902221218_add_message_to_solidus_subscriptions_installment_details.rb +5 -5
  69. data/db/migrate/20160922164101_add_interval_length_and_units_to_subscription_line_items.rb +8 -8
  70. data/db/migrate/20161006191003_add_skip_count_to_solidus_subscriptions_subscriptions.rb +5 -5
  71. data/db/migrate/20161006191127_add_successive_skip_count_to_solidus_subscriptions_subscriptions.rb +5 -5
  72. data/db/migrate/20161014212649_allow_spree_line_item_id_to_be_null.rb +5 -5
  73. data/db/migrate/20161017155749_add_order_id_to_solidus_subscriptions_installment_details.rb +6 -6
  74. data/db/migrate/20161017175509_remove_order_id_from_solidus_subscriptions_installments.rb +6 -6
  75. data/db/migrate/20161017201944_add_subscription_order_to_spree_orders.rb +5 -5
  76. data/db/migrate/20161221155142_add_store_to_solidus_subscriptions_subscriptions.rb +6 -6
  77. data/db/migrate/20161223152905_add_address_id_to_solidus_subscriptions_subscriptions.rb +7 -7
  78. data/db/migrate/20170106224713_change_line_item_max_installments_to_end_date.rb +6 -6
  79. data/db/migrate/20170111224458_change_subscription_actionable_date_to_datetime.rb +5 -5
  80. data/db/migrate/20170111232801_change_inteval_actionable_date_to_datetime.rb +5 -5
  81. data/db/migrate/20170112012407_add_config_options_to_subscriptions.rb +7 -7
  82. data/lib/generators/solidus_subscriptions/install/install_generator.rb +30 -30
  83. data/lib/solidus_subscriptions.rb +6 -6
  84. data/lib/solidus_subscriptions/ability.rb +19 -19
  85. data/lib/solidus_subscriptions/config.rb +97 -97
  86. data/lib/solidus_subscriptions/engine.rb +56 -56
  87. data/lib/solidus_subscriptions/permitted_attributes.rb +36 -36
  88. data/lib/solidus_subscriptions/processor.rb +108 -108
  89. data/lib/solidus_subscriptions/testing_support/factories.rb +5 -5
  90. data/lib/solidus_subscriptions/testing_support/factories/installment_detail_factory.rb +7 -7
  91. data/lib/solidus_subscriptions/testing_support/factories/installment_factory.rb +21 -21
  92. data/lib/solidus_subscriptions/testing_support/factories/line_item_factory.rb +18 -18
  93. data/lib/solidus_subscriptions/testing_support/factories/spree/line_item_factory.rb +17 -17
  94. data/lib/solidus_subscriptions/testing_support/factories/spree/order_factory.rb +18 -18
  95. data/lib/solidus_subscriptions/testing_support/factories/spree_modification_factory.rb +8 -8
  96. data/lib/solidus_subscriptions/testing_support/factories/subscription_factory.rb +43 -43
  97. data/lib/solidus_subscriptions/version.rb +3 -3
  98. data/lib/solidus_subscriptions/version.rb~ +3 -0
  99. data/lib/tasks/process_subscriptions.rake +6 -6
  100. metadata +4 -3
@@ -1,60 +1,60 @@
1
- # This module is responsible for taking SolidusSubscriptions::LineItem
2
- # objects and creating SolidusSubscriptions::Subscription Objects
3
- module SolidusSubscriptions
4
- module SubscriptionGenerator
5
- extend self
6
-
7
- SubscriptionConfiguration = Struct.new(:interval_length, :interval_units, :end_date)
8
-
9
- # Create and persist a subscription for a collection of subscription
10
- # line items
11
- #
12
- # @param subscription_line_items [Array<SolidusSubscriptions::LineItem>] The
13
- # subscription_line_items to be activated
14
- #
15
- # @return [SolidusSubscriptions::Subscription]
16
- def activate(subscription_line_items)
17
- return if subscription_line_items.empty?
18
-
19
- order = subscription_line_items.first.order
20
- configuration = subscription_configuration(subscription_line_items.first)
21
-
22
- subscription_attributes = {
23
- user: order.user,
24
- line_items: subscription_line_items,
25
- store: order.store,
26
- shipping_address: order.ship_address,
27
- **configuration.to_h
28
- }
29
-
30
- Subscription.create!(subscription_attributes) do |sub|
31
- sub.actionable_date = sub.next_actionable_date
32
- end
33
- end
34
-
35
- # Group a collection of line items by common subscription configuration
36
- # options. Grouped subscription_line_items can belong to a single
37
- # subscription.
38
- #
39
- # @param subscription_line_items [Array<SolidusSubscriptions::LineItem>] The
40
- # subscription_line_items to be grouped.
41
- #
42
- # @return [Array<Array<SolidusSubscriptions::LineItem>>]
43
- def group(subscription_line_items)
44
- subscription_line_items.group_by do |li|
45
- subscription_configuration(li)
46
- end.
47
- values
48
- end
49
-
50
- private
51
-
52
- def subscription_configuration(subscription_line_item)
53
- SubscriptionConfiguration.new(
54
- subscription_line_item.interval_length,
55
- subscription_line_item.interval_units,
56
- subscription_line_item.end_date
57
- )
58
- end
59
- end
60
- end
1
+ # This module is responsible for taking SolidusSubscriptions::LineItem
2
+ # objects and creating SolidusSubscriptions::Subscription Objects
3
+ module SolidusSubscriptions
4
+ module SubscriptionGenerator
5
+ extend self
6
+
7
+ SubscriptionConfiguration = Struct.new(:interval_length, :interval_units, :end_date)
8
+
9
+ # Create and persist a subscription for a collection of subscription
10
+ # line items
11
+ #
12
+ # @param subscription_line_items [Array<SolidusSubscriptions::LineItem>] The
13
+ # subscription_line_items to be activated
14
+ #
15
+ # @return [SolidusSubscriptions::Subscription]
16
+ def activate(subscription_line_items)
17
+ return if subscription_line_items.empty?
18
+
19
+ order = subscription_line_items.first.order
20
+ configuration = subscription_configuration(subscription_line_items.first)
21
+
22
+ subscription_attributes = {
23
+ user: order.user,
24
+ line_items: subscription_line_items,
25
+ store: order.store,
26
+ shipping_address: order.ship_address,
27
+ **configuration.to_h
28
+ }
29
+
30
+ Subscription.create!(subscription_attributes) do |sub|
31
+ sub.actionable_date = sub.next_actionable_date
32
+ end
33
+ end
34
+
35
+ # Group a collection of line items by common subscription configuration
36
+ # options. Grouped subscription_line_items can belong to a single
37
+ # subscription.
38
+ #
39
+ # @param subscription_line_items [Array<SolidusSubscriptions::LineItem>] The
40
+ # subscription_line_items to be grouped.
41
+ #
42
+ # @return [Array<Array<SolidusSubscriptions::LineItem>>]
43
+ def group(subscription_line_items)
44
+ subscription_line_items.group_by do |li|
45
+ subscription_configuration(li)
46
+ end.
47
+ values
48
+ end
49
+
50
+ private
51
+
52
+ def subscription_configuration(subscription_line_item)
53
+ SubscriptionConfiguration.new(
54
+ subscription_line_item.interval_length,
55
+ subscription_line_item.interval_units,
56
+ subscription_line_item.end_date
57
+ )
58
+ end
59
+ end
60
+ end
@@ -1,21 +1,21 @@
1
- module SolidusSubscriptions
2
- module SubscriptionLineItemBuilder
3
- private
4
-
5
- def create_subscription_line_item(line_item)
6
- SolidusSubscriptions::LineItem.create!(
7
- subscription_params.merge(spree_line_item: line_item)
8
- )
9
-
10
- # Rerun the promotion handler to pickup subscription promotions
11
- Spree::PromotionHandler::Cart.new(line_item.order).activate
12
- line_item.order.update!
13
- end
14
-
15
- def subscription_params
16
- params.require(:subscription_line_item).permit(
17
- SolidusSubscriptions::Config.subscription_line_item_attributes
18
- )
19
- end
20
- end
21
- end
1
+ module SolidusSubscriptions
2
+ module SubscriptionLineItemBuilder
3
+ private
4
+
5
+ def create_subscription_line_item(line_item)
6
+ SolidusSubscriptions::LineItem.create!(
7
+ subscription_params.merge(spree_line_item: line_item)
8
+ )
9
+
10
+ # Rerun the promotion handler to pickup subscription promotions
11
+ Spree::PromotionHandler::Cart.new(line_item.order).activate
12
+ line_item.order.update!
13
+ end
14
+
15
+ def subscription_params
16
+ params.require(:subscription_line_item).permit(
17
+ SolidusSubscriptions::Config.subscription_line_item_attributes
18
+ )
19
+ end
20
+ end
21
+ end
@@ -1,25 +1,25 @@
1
- module SolidusSubscriptions
2
- class SubscriptionOrderPromotionRule < Spree::PromotionRule
3
- # Promotion can be applied to an entire order. Will only be true
4
- # for Spree::Order
5
- #
6
- # @param promotable [Object] Any object which could have this
7
- # promotion rule applied to it.
8
- #
9
- # @return [Boolean]
10
- def applicable?(promotable)
11
- promotable.is_a? Spree::Order
12
- end
13
-
14
- # An order is eligible if it fulfills a subscription Installment. Will only
15
- # return true if the order fulfills one or more Installments
16
- #
17
- # @param order [Spree::Order] The order which could have this rule applied
18
- # to it.
19
- #
20
- # @return [Boolean]
21
- def eligible?(order, **_options)
22
- order.subscription_order?
23
- end
24
- end
25
- end
1
+ module SolidusSubscriptions
2
+ class SubscriptionOrderPromotionRule < Spree::PromotionRule
3
+ # Promotion can be applied to an entire order. Will only be true
4
+ # for Spree::Order
5
+ #
6
+ # @param promotable [Object] Any object which could have this
7
+ # promotion rule applied to it.
8
+ #
9
+ # @return [Boolean]
10
+ def applicable?(promotable)
11
+ promotable.is_a? Spree::Order
12
+ end
13
+
14
+ # An order is eligible if it fulfills a subscription Installment. Will only
15
+ # return true if the order fulfills one or more Installments
16
+ #
17
+ # @param order [Spree::Order] The order which could have this rule applied
18
+ # to it.
19
+ #
20
+ # @return [Boolean]
21
+ def eligible?(order, **_options)
22
+ order.subscription_order?
23
+ end
24
+ end
25
+ end
@@ -1,38 +1,38 @@
1
- module SolidusSubscriptions
2
- class SubscriptionPromotionRule < Spree::PromotionRule
3
- # Promotion can be applied to an entire order. Will only be true
4
- # for Spree::Order
5
- #
6
- # @param promotable [Object] Any object which could have this
7
- # promotion rule applied to it.
8
- #
9
- # @return [Boolean]
10
- def applicable?(promotable)
11
- promotable.is_a? Spree::Order
12
- end
13
-
14
- # An order is eligible if it contains a line item with an associates
15
- # subscription_line_item. This rule applies to order and so its eligibility
16
- # will always be considered against an order. Will only return true for
17
- # orders containing Spree::Line item with associated subscription_line_items
18
- #
19
- # @param order [Spree::Order] The order which could have this rule applied
20
- # to it.
21
- #
22
- # @return [Boolean]
23
- def eligible?(order, **_options)
24
- order.subscription_line_items.any?
25
- end
26
-
27
- # Certain actions create adjustments on line items. In this case, only
28
- # line items with associated subscription_line_itms are eligible to be
29
- # adjusted. Will only return true # if :line_item has an associated
30
- # subscription.
31
- #
32
- # @param line_item [Spree::LineItem] The line item which could be adjusted
33
- # by the promotion.
34
- def actionable?(line_item)
35
- line_item.subscription_line_items.present?
36
- end
37
- end
38
- end
1
+ module SolidusSubscriptions
2
+ class SubscriptionPromotionRule < Spree::PromotionRule
3
+ # Promotion can be applied to an entire order. Will only be true
4
+ # for Spree::Order
5
+ #
6
+ # @param promotable [Object] Any object which could have this
7
+ # promotion rule applied to it.
8
+ #
9
+ # @return [Boolean]
10
+ def applicable?(promotable)
11
+ promotable.is_a? Spree::Order
12
+ end
13
+
14
+ # An order is eligible if it contains a line item with an associates
15
+ # subscription_line_item. This rule applies to order and so its eligibility
16
+ # will always be considered against an order. Will only return true for
17
+ # orders containing Spree::Line item with associated subscription_line_items
18
+ #
19
+ # @param order [Spree::Order] The order which could have this rule applied
20
+ # to it.
21
+ #
22
+ # @return [Boolean]
23
+ def eligible?(order, **_options)
24
+ order.subscription_line_items.any?
25
+ end
26
+
27
+ # Certain actions create adjustments on line items. In this case, only
28
+ # line items with associated subscription_line_itms are eligible to be
29
+ # adjusted. Will only return true # if :line_item has an associated
30
+ # subscription.
31
+ #
32
+ # @param line_item [Spree::LineItem] The line item which could be adjusted
33
+ # by the promotion.
34
+ def actionable?(line_item)
35
+ line_item.subscription_line_items.present?
36
+ end
37
+ end
38
+ end
@@ -1,16 +1,16 @@
1
- # This service class is intented to provide callback behaviour to handle
2
- # an installment successfully being processed
3
- module SolidusSubscriptions
4
- class SuccessDispatcher < Dispatcher
5
- def dispatch
6
- installments.each { |i| i.success!(order) }
7
- super
8
- end
9
-
10
- private
11
-
12
- def message
13
- "Successfully processed installments: #{installments.map(&:id).join(', ')}"
14
- end
15
- end
16
- end
1
+ # This service class is intented to provide callback behaviour to handle
2
+ # an installment successfully being processed
3
+ module SolidusSubscriptions
4
+ class SuccessDispatcher < Dispatcher
5
+ def dispatch
6
+ installments.each { |i| i.success!(order) }
7
+ super
8
+ end
9
+
10
+ private
11
+
12
+ def message
13
+ "Successfully processed installments: #{installments.map(&:id).join(', ')}"
14
+ end
15
+ end
16
+ end
@@ -1,17 +1,17 @@
1
- # This error should be raised if a user attempts to subscribe to a item which
2
- # is not subscribable
3
- module SolidusSubscriptions
4
- class UnsubscribableError < StandardError
5
- def initialize(subscribable)
6
- @subscribable = subscribable
7
- super
8
- end
9
-
10
- def to_s
11
- <<-MSG.squish
12
- #{@subscribable.class} with id: #{@subscribable.id} cannot be
13
- subscribed to.
14
- MSG
15
- end
16
- end
17
- end
1
+ # This error should be raised if a user attempts to subscribe to a item which
2
+ # is not subscribable
3
+ module SolidusSubscriptions
4
+ class UnsubscribableError < StandardError
5
+ def initialize(subscribable)
6
+ @subscribable = subscribable
7
+ super
8
+ end
9
+
10
+ def to_s
11
+ <<-MSG.squish
12
+ #{@subscribable.class} with id: #{@subscribable.id} cannot be
13
+ subscribed to.
14
+ MSG
15
+ end
16
+ end
17
+ end
@@ -1,15 +1,15 @@
1
- module SolidusSubscriptions
2
- class UserMismatchError < StandardError
3
- def initialize(installments)
4
- @installments = installments
5
- end
6
-
7
- def to_s
8
- <<-MSG.squish
9
- Installments must have the same user to be processed as a consolidated
10
- installment. Could not process installments:
11
- #{@installments.map(&:id).join(', ')}
12
- MSG
13
- end
14
- end
15
- end
1
+ module SolidusSubscriptions
2
+ class UserMismatchError < StandardError
3
+ def initialize(installments)
4
+ @installments = installments
5
+ end
6
+
7
+ def to_s
8
+ <<-MSG.squish
9
+ Installments must have the same user to be processed as a consolidated
10
+ installment. Could not process installments:
11
+ #{@installments.map(&:id).join(', ')}
12
+ MSG
13
+ end
14
+ end
15
+ end
@@ -1,13 +1,13 @@
1
- Deface::Override.new(
2
- virtual_path: "spree/admin/variants/_form",
3
- name: "solidus_subscriptions_subscribable_checkbox",
4
- insert_after: "[data-hook='track_inventory']",
5
- partial: "spree/admin/variants/subscribable_checkbox"
6
- )
7
-
8
- Deface::Override.new(
9
- virtual_path: "spree/admin/products/_form",
10
- name: "solidus_subscriptions_product_subscribable_checkbox",
11
- insert_after: "[data-hook='admin_product_form_meta']",
12
- partial: "spree/admin/products/subscribable_checkbox"
13
- )
1
+ Deface::Override.new(
2
+ virtual_path: "spree/admin/variants/_form",
3
+ name: "solidus_subscriptions_subscribable_checkbox",
4
+ insert_after: "[data-hook='track_inventory']",
5
+ partial: "spree/admin/variants/subscribable_checkbox"
6
+ )
7
+
8
+ Deface::Override.new(
9
+ virtual_path: "spree/admin/products/_form",
10
+ name: "solidus_subscriptions_product_subscribable_checkbox",
11
+ insert_after: "[data-hook='admin_product_form_meta']",
12
+ partial: "spree/admin/products/subscribable_checkbox"
13
+ )
@@ -1,8 +1,8 @@
1
- if !Spree::Backend::Config.respond_to?(:menu_items)
2
- Deface::Override.new(
3
- virtual_path: 'spree/admin/shared/_menu',
4
- name: :add_subcriptions_admin_link,
5
- insert_bottom: "[data-hook='admin_tabs']",
6
- partial: 'spree/admin/shared/subscription_tab'
7
- )
8
- end
1
+ if !Spree::Backend::Config.respond_to?(:menu_items)
2
+ Deface::Override.new(
3
+ virtual_path: 'spree/admin/shared/_menu',
4
+ name: :add_subcriptions_admin_link,
5
+ insert_bottom: "[data-hook='admin_tabs']",
6
+ partial: 'spree/admin/shared/subscription_tab'
7
+ )
8
+ end
@@ -1,6 +1,6 @@
1
- Deface::Override.new(
2
- virtual_path: "spree/products/_cart_form",
3
- name: "subscription_line_item_fields",
4
- insert_after: "[data-hook='inside_product_cart_form']",
5
- partial: "spree/frontend/products/subscription_line_item_fields"
6
- )
1
+ Deface::Override.new(
2
+ virtual_path: "spree/products/_cart_form",
3
+ name: "subscription_line_item_fields",
4
+ insert_after: "[data-hook='inside_product_cart_form']",
5
+ partial: "spree/frontend/products/subscription_line_item_fields"
6
+ )