spree_account_recurring 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.
- data/LICENSE +26 -0
- data/README.md +108 -0
- data/app/assets/javascripts/admin/spree_account_recurring.js +1 -0
- data/app/assets/javascripts/store/spree_account_recurring.js +1 -0
- data/app/assets/javascripts/store/stripe.js +53 -0
- data/app/assets/stylesheets/admin/spree_account_recurring.css +3 -0
- data/app/assets/stylesheets/store/spree_account_recurring.css +3 -0
- data/app/controllers/concerns/spree/admin/ransack_date_search.rb +47 -0
- data/app/controllers/spree/admin/plans_controller.rb +63 -0
- data/app/controllers/spree/admin/recurrings_controller.rb +66 -0
- data/app/controllers/spree/admin/subscription_events_controller.rb +14 -0
- data/app/controllers/spree/admin/subscriptions_controller.rb +14 -0
- data/app/controllers/spree/plans_controller.rb +7 -0
- data/app/controllers/spree/recurring_hooks_controller.rb +53 -0
- data/app/controllers/spree/subscriptions_controller.rb +69 -0
- data/app/models/concerns/before_each.rb +21 -0
- data/app/models/concerns/restrictive_destroyer.rb +44 -0
- data/app/models/concerns/spree/plan/api_handler.rb +46 -0
- data/app/models/concerns/spree/recurring/stripe_recurring/api_handler.rb +28 -0
- data/app/models/concerns/spree/recurring/stripe_recurring/api_handler/plan_api_handler.rb +49 -0
- data/app/models/concerns/spree/recurring/stripe_recurring/api_handler/subscription_api_handler.rb +20 -0
- data/app/models/concerns/spree/recurring/stripe_recurring/api_handler/subscription_event_api_handler.rb +19 -0
- data/app/models/concerns/spree/subscription/api_handler.rb +38 -0
- data/app/models/concerns/spree/subscription/role_subscriber.rb +36 -0
- data/app/models/spree/plan.rb +31 -0
- data/app/models/spree/recurring.rb +27 -0
- data/app/models/spree/recurring/stripe_recurring.rb +16 -0
- data/app/models/spree/subscriber_ability.rb +17 -0
- data/app/models/spree/subscription.rb +33 -0
- data/app/models/spree/subscription_event.rb +11 -0
- data/app/models/spree/user_decorator.rb +14 -0
- data/app/overrides/admin/view_decorator.rb +27 -0
- data/app/views/spree/admin/plans/_form.html.erb +47 -0
- data/app/views/spree/admin/plans/destroy.js.erb +0 -0
- data/app/views/spree/admin/plans/edit.html.erb +22 -0
- data/app/views/spree/admin/plans/index.html.erb +70 -0
- data/app/views/spree/admin/plans/new.html.erb +22 -0
- data/app/views/spree/admin/recurrings/_form.html.erb +42 -0
- data/app/views/spree/admin/recurrings/destroy.js.erb +0 -0
- data/app/views/spree/admin/recurrings/edit.html.erb +23 -0
- data/app/views/spree/admin/recurrings/index.html.erb +48 -0
- data/app/views/spree/admin/recurrings/new.html.erb +22 -0
- data/app/views/spree/admin/subscription_events/index.html.erb +72 -0
- data/app/views/spree/admin/subscriptions/index.html.erb +76 -0
- data/app/views/spree/plans/index.html.erb +14 -0
- data/app/views/spree/subscriptions/new.html.erb +36 -0
- data/app/views/spree/subscriptions/show.html.erb +4 -0
- data/config/initializers/stripe.rb +2 -0
- data/config/locales/en.yml +43 -0
- data/config/routes.rb +24 -0
- data/db/migrate/20131119054112_create_spree_recurring.rb +13 -0
- data/db/migrate/20131119054212_create_spree_plan.rb +21 -0
- data/db/migrate/20131119054322_create_spree_subscription.rb +16 -0
- data/db/migrate/20131125123820_create_spree_subscription_events.rb +14 -0
- data/db/migrate/20131202110012_add_subscriber_role_to_spree_roles.rb +15 -0
- data/db/migrate/20140301141327_add_stripe_customer_id_to_spree_users.rb +6 -0
- data/db/migrate/20140303072857_add_default_to_spree_plans.rb +6 -0
- data/db/migrate/20140319092254_add_response_to_spree_subscription_events.rb +5 -0
- data/lib/generators/spree_account_recurring/install/install_generator.rb +31 -0
- data/lib/spree_account_recurring.rb +2 -0
- data/lib/spree_account_recurring/engine.rb +22 -0
- data/lib/spree_account_recurring/factories.rb +6 -0
- data/lib/spree_account_recurring/testing_support/ransack_date_search_helper.rb +125 -0
- metadata +188 -0
| @@ -0,0 +1,76 @@ | |
| 1 | 
            +
            <% content_for :page_title do %>
         | 
| 2 | 
            +
              <%= Spree.t(:subscription) %>
         | 
| 3 | 
            +
            <% end %>
         | 
| 4 | 
            +
             | 
| 5 | 
            +
            <% content_for :page_actions do %>
         | 
| 6 | 
            +
              <li><%= link_to_with_icon 'icon-arrow-left', Spree.t(:back_to_reports_list), spree.admin_reports_url, :class => 'button' %></li>
         | 
| 7 | 
            +
            <% end %>
         | 
| 8 | 
            +
             | 
| 9 | 
            +
            <% content_for :table_filter_title do %>
         | 
| 10 | 
            +
              <%= Spree.t(:subscription_date_search) %>
         | 
| 11 | 
            +
            <% end %>
         | 
| 12 | 
            +
             | 
| 13 | 
            +
            <% content_for :table_filter do %>
         | 
| 14 | 
            +
              <%= search_form_for @search, :url => spree.admin_subscriptions_url  do |s| %>
         | 
| 15 | 
            +
                <div class="date-range-filter field align-center">
         | 
| 16 | 
            +
                  <%= label_tag nil, Spree.t(:start), :class => 'inline' %>
         | 
| 17 | 
            +
                  <%= s.text_field :subscribed_at_gt, :class => 'datepicker datepicker-from', :value => datepicker_field_value(params[:q][:subscribed_at_gt]) %>
         | 
| 18 | 
            +
                  
         | 
| 19 | 
            +
                  <span class="range-divider">
         | 
| 20 | 
            +
                    <i class="icon-arrow-right"></i>
         | 
| 21 | 
            +
                  </span>
         | 
| 22 | 
            +
             | 
| 23 | 
            +
                  <%= s.text_field :subscribed_at_lt, :class => 'datepicker datepicker-to', :value => datepicker_field_value(params[:q][:subscribed_at_lt]) %>
         | 
| 24 | 
            +
                  <%= label_tag nil, Spree.t(:end), :class => 'inline' %>
         | 
| 25 | 
            +
                </div>
         | 
| 26 | 
            +
             | 
| 27 | 
            +
                <div class="date-range-filter field align-center">
         | 
| 28 | 
            +
                  <%= label_tag nil, Spree.t(:email), :class => 'inline' %>
         | 
| 29 | 
            +
                  <%= s.text_field :email_eq, style: "width:240px" %>
         | 
| 30 | 
            +
                </div>
         | 
| 31 | 
            +
             | 
| 32 | 
            +
                <div class="actions filter-actions">
         | 
| 33 | 
            +
                  <%= button Spree.t(:search), 'icon-search'  %>
         | 
| 34 | 
            +
                </div>
         | 
| 35 | 
            +
              <% end %>
         | 
| 36 | 
            +
            <% end %>
         | 
| 37 | 
            +
             | 
| 38 | 
            +
            <% if @subscriptions.any? %>
         | 
| 39 | 
            +
              <table class="index" id='listing_subscriptions'>
         | 
| 40 | 
            +
                <colgroup>
         | 
| 41 | 
            +
                  <col style="width: 30%">
         | 
| 42 | 
            +
                  <col style="width: 20%">
         | 
| 43 | 
            +
                  <col style="width: 15%">
         | 
| 44 | 
            +
                  <col style="width: 15%">
         | 
| 45 | 
            +
                  <col style="width: 20%">
         | 
| 46 | 
            +
                </colgroup>
         | 
| 47 | 
            +
                <thead>
         | 
| 48 | 
            +
                  <tr data-hook="admin_subscriptions_index_headers">
         | 
| 49 | 
            +
                    <th><%= Spree.t(:email) %></th>
         | 
| 50 | 
            +
                    <th><%= Spree.t(:plan) %></th>
         | 
| 51 | 
            +
                    <th><%= Spree.t(:subscribed_at) %></th>
         | 
| 52 | 
            +
                    <th><%= Spree.t(:unsubscribed_at) %></th>
         | 
| 53 | 
            +
                    <th data-hook="admin_recurring_plans_index_header_actions" class="actions"></th>
         | 
| 54 | 
            +
                  </tr>
         | 
| 55 | 
            +
                </thead>
         | 
| 56 | 
            +
                <tbody>
         | 
| 57 | 
            +
                  <% @subscriptions.each do |subscription|%>
         | 
| 58 | 
            +
                    <tr data-hook="admin_subscriptions_index_rows" class="<%= cycle('odd', 'even')%>">
         | 
| 59 | 
            +
                      <td class="align-center"><%= subscription.email %></td>
         | 
| 60 | 
            +
                      <td class="align-center"><%= link_to subscription.plan.api_plan_id, edit_admin_recurring_plan_url(subscription.plan.recurring, subscription.plan) %></td>
         | 
| 61 | 
            +
                      <td class="align-center"><%= subscription.subscribed_at.try(:strftime, '%d-%h-%Y') %></td>
         | 
| 62 | 
            +
                      <td class="align-center"><%= subscription.unsubscribed_at.try(:strftime, '%d-%h-%Y') || 'N/A' %></td>
         | 
| 63 | 
            +
                      <td data-hook="admin_recurring_plans_index_row_actions" class="actions">
         | 
| 64 | 
            +
                        <%= link_to Spree.t(:view_events), admin_subscription_events_url(q: {subscription_email_eq: subscription.email}) %>
         | 
| 65 | 
            +
                      </td>
         | 
| 66 | 
            +
                    </tr>
         | 
| 67 | 
            +
                  <% end %>
         | 
| 68 | 
            +
                </tbody>
         | 
| 69 | 
            +
              </table>
         | 
| 70 | 
            +
              
         | 
| 71 | 
            +
              <%= paginate @subscriptions %>
         | 
| 72 | 
            +
            <% else %>
         | 
| 73 | 
            +
              <div class="alpha sixteen columns no-objects-found">
         | 
| 74 | 
            +
                <%= Spree.t(:no_resource_found, resource: I18n.t(:other, scope: 'activerecord.models.spree/subscription')) %>
         | 
| 75 | 
            +
              </div>
         | 
| 76 | 
            +
            <% end %>
         | 
| @@ -0,0 +1,14 @@ | |
| 1 | 
            +
            <h2><%= Spree.t(:plans) %></h2>
         | 
| 2 | 
            +
            <br/>
         | 
| 3 | 
            +
            <% @plans.each do |plan| %>
         | 
| 4 | 
            +
              <div style='float:left;padding:20px;border:solid'>
         | 
| 5 | 
            +
                <strong><%= plan.name %></strong><br/>
         | 
| 6 | 
            +
                <%= number_to_currency plan.amount %> every <%= plan.interval_count %> <%= plan.interval.pluralize(plan.interval_count) %><br/>
         | 
| 7 | 
            +
                <%= plan.trial_period_days %> <%= 'day'.pluralize(plan.trial_period_days) %> trial <br/>
         | 
| 8 | 
            +
                <br/>
         | 
| 9 | 
            +
                <% if spree_current_user %>
         | 
| 10 | 
            +
                  <%= button_link_to 'Subscribe', new_recurring_plan_subscription_url(plan) %>
         | 
| 11 | 
            +
                <% end %>
         | 
| 12 | 
            +
              </div>
         | 
| 13 | 
            +
            <% end %>
         | 
| 14 | 
            +
            <br style='clear:both'/>
         | 
| @@ -0,0 +1,36 @@ | |
| 1 | 
            +
            <%= render :partial => 'spree/shared/error_messages', :locals => { :target => @subscription } %>
         | 
| 2 | 
            +
             | 
| 3 | 
            +
            <%= form_for @subscription, url: recurring_plan_subscriptions_url(@plan) do |f| %>
         | 
| 4 | 
            +
              <%= image_tag 'credit_cards/credit_card.gif', :id => 'credit-card-image' %>
         | 
| 5 | 
            +
             | 
| 6 | 
            +
              <div id="plan_<%= @plan.id %>_subscribe">
         | 
| 7 | 
            +
                <p class="field" data-hook="card_number">
         | 
| 8 | 
            +
                  <%= label_tag "card_number", Spree.t(:card_number) %><span class="required">*</span><br />
         | 
| 9 | 
            +
                  <% options_hash = Rails.env.production? ? {:autocomplete => 'off'} : {} %>
         | 
| 10 | 
            +
                  <%= text_field_tag "card_number", '', options_hash.merge(:id => 'card_number', :class => 'required cardNumber', :size => 19, :maxlength => 19, :autocomplete => "off") %>
         | 
| 11 | 
            +
                   
         | 
| 12 | 
            +
                  <span id="card_type" style="display:none;">
         | 
| 13 | 
            +
                    ( <span id="looks_like" ><%= Spree.t(:card_type_is) %> <span id="type"></span></span>
         | 
| 14 | 
            +
                      <span id="unrecognized"><%= Spree.t(:unrecognized_card_type) %></span>
         | 
| 15 | 
            +
                    )
         | 
| 16 | 
            +
                  </span>
         | 
| 17 | 
            +
                </p>
         | 
| 18 | 
            +
                <p class="field" data-hook="card_expiration">
         | 
| 19 | 
            +
                  <%= label_tag "card_expiry", Spree.t(:expiration) %><span class="required">*</span><br />
         | 
| 20 | 
            +
                  <%= text_field_tag "card_expiry", '', :id => 'card_expiry', :class => "required cardExpiry", :placeholder => "MM / YY" %>
         | 
| 21 | 
            +
                </p>
         | 
| 22 | 
            +
                <p class="field" data-hook="card_code">
         | 
| 23 | 
            +
                  <%= label_tag "card_code", Spree.t(:card_code) %><span class="required">*</span><br />
         | 
| 24 | 
            +
                  <%= text_field_tag "card_code", '', options_hash.merge(:id => 'card_code', :class => 'required cardCode', :size => 5) %>
         | 
| 25 | 
            +
                  <%= link_to "(#{Spree.t(:what_is_this)})", spree.content_path('cvv'), :target => '_blank', "data-hook" => "cvv_link", :id => "cvv_link" %>
         | 
| 26 | 
            +
                </p>
         | 
| 27 | 
            +
              </div>
         | 
| 28 | 
            +
              
         | 
| 29 | 
            +
              <%= f.submit Spree.t(:subscribe), class: 'continue' %>
         | 
| 30 | 
            +
              <script>Spree.disableSaveOnClick();</script>
         | 
| 31 | 
            +
            <% end %>
         | 
| 32 | 
            +
             | 
| 33 | 
            +
            <script type="text/javascript" src="https://js.stripe.com/v2/"></script>
         | 
| 34 | 
            +
            <script type="text/javascript">Stripe.setPublishableKey("<%= @plan.provider.preferred_public_key %>");</script>
         | 
| 35 | 
            +
            <script>Spree.stripePaymentMethod = $('#plan_' + <%= @plan.id %> + '_subscribe')</script>
         | 
| 36 | 
            +
            <%= javascript_include_tag "store/stripe" %>
         | 
| @@ -0,0 +1,43 @@ | |
| 1 | 
            +
            en:
         | 
| 2 | 
            +
              activerecord:
         | 
| 3 | 
            +
                models:
         | 
| 4 | 
            +
                  spree/recurring:
         | 
| 5 | 
            +
                    one: Recurring
         | 
| 6 | 
            +
                    other: Recurrings
         | 
| 7 | 
            +
                  spree/plan:
         | 
| 8 | 
            +
                    one: Plan
         | 
| 9 | 
            +
                    other: Plans
         | 
| 10 | 
            +
                  spree/subscription:
         | 
| 11 | 
            +
                    one: Subscription
         | 
| 12 | 
            +
                    other: Subscriptions
         | 
| 13 | 
            +
                  spree/subscription_event:
         | 
| 14 | 
            +
                    one: Subscription Event
         | 
| 15 | 
            +
                    other: Subscription Events
         | 
| 16 | 
            +
              spree:
         | 
| 17 | 
            +
                api_plan_id: API Plan ID
         | 
| 18 | 
            +
                amount: Amount
         | 
| 19 | 
            +
                back_to_recurrings_list: Back To Recurrings List
         | 
| 20 | 
            +
                back_to_plans_list: Back To Plans List
         | 
| 21 | 
            +
                currency: Currency
         | 
| 22 | 
            +
                editing_recurring: Editing Recurring
         | 
| 23 | 
            +
                editing_plan: Editing Plan
         | 
| 24 | 
            +
                every: Every
         | 
| 25 | 
            +
                interval: Interval
         | 
| 26 | 
            +
                interval_count: Interval Count
         | 
| 27 | 
            +
                manage_plans: Manage Plans
         | 
| 28 | 
            +
                name: Name
         | 
| 29 | 
            +
                new_recurring: New Recurring
         | 
| 30 | 
            +
                new_plan: New Plan
         | 
| 31 | 
            +
                plans: Plans
         | 
| 32 | 
            +
                recurring: Recurring
         | 
| 33 | 
            +
                request_type: Request Type
         | 
| 34 | 
            +
                subscribe: Subscribe
         | 
| 35 | 
            +
                subscriptions: Subscriptions
         | 
| 36 | 
            +
                subscription_events: Subscription Events
         | 
| 37 | 
            +
                subscription_search: Subscription Search
         | 
| 38 | 
            +
                subscription_event_search: Subscription Event Search
         | 
| 39 | 
            +
                subscribed_at: Subscribed At
         | 
| 40 | 
            +
                unsubscribed_at: Unsubscribed At
         | 
| 41 | 
            +
                trial_period_days: Trial Period Days
         | 
| 42 | 
            +
                unsubscribe: Unsubscribe
         | 
| 43 | 
            +
                view_events: View Events
         | 
    
        data/config/routes.rb
    ADDED
    
    | @@ -0,0 +1,24 @@ | |
| 1 | 
            +
            Spree::Core::Engine.routes.draw do
         | 
| 2 | 
            +
              namespace :admin do
         | 
| 3 | 
            +
                resources :recurrings, except: :show do
         | 
| 4 | 
            +
                  resources :plans, except: :show
         | 
| 5 | 
            +
                end
         | 
| 6 | 
            +
             | 
| 7 | 
            +
                resources :reports, only: :index do
         | 
| 8 | 
            +
                  collection do
         | 
| 9 | 
            +
                    resources :subscriptions, only: :index
         | 
| 10 | 
            +
                    resources :subscription_events, only: :index
         | 
| 11 | 
            +
                  end
         | 
| 12 | 
            +
                end
         | 
| 13 | 
            +
              end
         | 
| 14 | 
            +
             | 
| 15 | 
            +
              resources :recurring_hooks, only: :none do
         | 
| 16 | 
            +
                post :handler, on: :collection
         | 
| 17 | 
            +
              end
         | 
| 18 | 
            +
             | 
| 19 | 
            +
              namespace :recurring do
         | 
| 20 | 
            +
                resources :plans, only: :index do
         | 
| 21 | 
            +
                  resources :subscriptions, only: [:show, :create, :destroy, :new]
         | 
| 22 | 
            +
                end
         | 
| 23 | 
            +
              end
         | 
| 24 | 
            +
            end
         | 
| @@ -0,0 +1,13 @@ | |
| 1 | 
            +
            class CreateSpreeRecurring < ActiveRecord::Migration
         | 
| 2 | 
            +
              def change
         | 
| 3 | 
            +
                create_table :spree_recurrings do |t|
         | 
| 4 | 
            +
                  t.string :name
         | 
| 5 | 
            +
                  t.string :type
         | 
| 6 | 
            +
                  t.text :description
         | 
| 7 | 
            +
                  t.boolean :active
         | 
| 8 | 
            +
                  t.datetime :deleted_at
         | 
| 9 | 
            +
                end
         | 
| 10 | 
            +
             | 
| 11 | 
            +
                add_index :spree_recurrings, :deleted_at
         | 
| 12 | 
            +
              end
         | 
| 13 | 
            +
            end
         | 
| @@ -0,0 +1,21 @@ | |
| 1 | 
            +
            class CreateSpreePlan < ActiveRecord::Migration
         | 
| 2 | 
            +
              def change
         | 
| 3 | 
            +
                create_table :spree_plans do |t|
         | 
| 4 | 
            +
                  t.string :api_plan_id, nil: false
         | 
| 5 | 
            +
                  t.integer :amount
         | 
| 6 | 
            +
                  t.string :interval
         | 
| 7 | 
            +
                  t.integer :interval_count, :default => 1
         | 
| 8 | 
            +
                  t.string :name
         | 
| 9 | 
            +
                  t.string :currency
         | 
| 10 | 
            +
                  t.integer :recurring_id
         | 
| 11 | 
            +
                  t.integer :trial_period_days, :default => 0
         | 
| 12 | 
            +
                  t.boolean :active, :default => false
         | 
| 13 | 
            +
                  t.datetime :deleted_at
         | 
| 14 | 
            +
                end
         | 
| 15 | 
            +
             | 
| 16 | 
            +
                add_index :spree_plans, [:deleted_at, :recurring_id, :active]
         | 
| 17 | 
            +
                add_index :spree_plans, [:deleted_at, :active]
         | 
| 18 | 
            +
                add_index :spree_plans, [:deleted_at, :recurring_id]
         | 
| 19 | 
            +
                add_index :spree_plans, :deleted_at
         | 
| 20 | 
            +
              end
         | 
| 21 | 
            +
            end
         | 
| @@ -0,0 +1,16 @@ | |
| 1 | 
            +
            class CreateSpreeSubscription < ActiveRecord::Migration
         | 
| 2 | 
            +
              def change
         | 
| 3 | 
            +
                create_table :spree_subscriptions do |t|
         | 
| 4 | 
            +
                  t.integer :plan_id
         | 
| 5 | 
            +
                  t.string :email
         | 
| 6 | 
            +
                  t.integer :user_id
         | 
| 7 | 
            +
                  t.string :card_customer_token
         | 
| 8 | 
            +
                  t.datetime :subscribed_at
         | 
| 9 | 
            +
                  t.datetime :unsubscribed_at
         | 
| 10 | 
            +
                end
         | 
| 11 | 
            +
             | 
| 12 | 
            +
                add_index :spree_subscriptions, :subscribed_at
         | 
| 13 | 
            +
                add_index :spree_subscriptions, :unsubscribed_at
         | 
| 14 | 
            +
                add_index :spree_subscriptions, :plan_id
         | 
| 15 | 
            +
              end
         | 
| 16 | 
            +
            end
         | 
| @@ -0,0 +1,14 @@ | |
| 1 | 
            +
            class CreateSpreeSubscriptionEvents < ActiveRecord::Migration
         | 
| 2 | 
            +
              def change
         | 
| 3 | 
            +
                create_table :spree_subscription_events do |t|
         | 
| 4 | 
            +
                  t.string :event_id
         | 
| 5 | 
            +
                  t.integer :subscription_id
         | 
| 6 | 
            +
                  t.string :request_type
         | 
| 7 | 
            +
                  t.datetime :created_at, :null => false
         | 
| 8 | 
            +
                  t.datetime :updated_at, :null => false
         | 
| 9 | 
            +
                end
         | 
| 10 | 
            +
             | 
| 11 | 
            +
                add_index :spree_subscription_events, :subscription_id
         | 
| 12 | 
            +
                add_index :spree_subscription_events, :event_id
         | 
| 13 | 
            +
              end
         | 
| 14 | 
            +
            end
         | 
| @@ -0,0 +1,15 @@ | |
| 1 | 
            +
            class AddSubscriberRoleToSpreeRoles < ActiveRecord::Migration
         | 
| 2 | 
            +
              def up
         | 
| 3 | 
            +
                Spree::Role.where(name: "subscriber").first_or_create
         | 
| 4 | 
            +
                Spree::Subscription.includes(:user).uniq.each do |subscription|
         | 
| 5 | 
            +
                  subscription.add_role_subscriber unless subscription.user.has_spree_role?('subscriber')
         | 
| 6 | 
            +
                end
         | 
| 7 | 
            +
              end
         | 
| 8 | 
            +
             | 
| 9 | 
            +
              def down
         | 
| 10 | 
            +
                Spree::Subscription.includes(:user).uniq.each do |subscription|
         | 
| 11 | 
            +
                  subscription.remove_role_subscriber if subscription.user.has_spree_role?('subscriber')
         | 
| 12 | 
            +
                end
         | 
| 13 | 
            +
                Spree::Role.where(name: "subscriber").first.try(:destroy)
         | 
| 14 | 
            +
              end
         | 
| 15 | 
            +
            end
         | 
| @@ -0,0 +1,31 @@ | |
| 1 | 
            +
            module SpreeAccountRecurring
         | 
| 2 | 
            +
              module Generators
         | 
| 3 | 
            +
                class InstallGenerator < Rails::Generators::Base
         | 
| 4 | 
            +
             | 
| 5 | 
            +
                  class_option :auto_run_migrations, :type => :boolean, :default => false
         | 
| 6 | 
            +
             | 
| 7 | 
            +
                  def add_javascripts
         | 
| 8 | 
            +
                    append_file 'app/assets/javascripts/store/all.js', "//= require store/spree_account_recurring\n"
         | 
| 9 | 
            +
                    append_file 'app/assets/javascripts/admin/all.js', "//= require admin/spree_account_recurring\n"
         | 
| 10 | 
            +
                  end
         | 
| 11 | 
            +
             | 
| 12 | 
            +
                  def add_stylesheets
         | 
| 13 | 
            +
                    inject_into_file 'app/assets/stylesheets/store/all.css', " *= require store/spree_account_recurring\n", :before => /\*\//, :verbose => true
         | 
| 14 | 
            +
                    inject_into_file 'app/assets/stylesheets/admin/all.css', " *= require admin/spree_account_recurring\n", :before => /\*\//, :verbose => true
         | 
| 15 | 
            +
                  end
         | 
| 16 | 
            +
             | 
| 17 | 
            +
                  def add_migrations
         | 
| 18 | 
            +
                    run 'bundle exec rake railties:install:migrations FROM=spree_account_recurring'
         | 
| 19 | 
            +
                  end
         | 
| 20 | 
            +
             | 
| 21 | 
            +
                  def run_migrations
         | 
| 22 | 
            +
                    run_migrations = options[:auto_run_migrations] || ['', 'y', 'Y'].include?(ask 'Would you like to run the migrations now? [Y/n]')
         | 
| 23 | 
            +
                    if run_migrations
         | 
| 24 | 
            +
                      run 'bundle exec rake db:migrate'
         | 
| 25 | 
            +
                    else
         | 
| 26 | 
            +
                      puts 'Skipping rake db:migrate, don\'t forget to run it!'
         | 
| 27 | 
            +
                    end
         | 
| 28 | 
            +
                  end
         | 
| 29 | 
            +
                end
         | 
| 30 | 
            +
              end
         | 
| 31 | 
            +
            end
         | 
| @@ -0,0 +1,22 @@ | |
| 1 | 
            +
            module SpreeAccountRecurring
         | 
| 2 | 
            +
              class Engine < Rails::Engine
         | 
| 3 | 
            +
                require 'spree/core'
         | 
| 4 | 
            +
                isolate_namespace Spree
         | 
| 5 | 
            +
                engine_name 'spree_account_recurring'
         | 
| 6 | 
            +
             | 
| 7 | 
            +
                config.autoload_paths += %W(#{config.root}/lib)
         | 
| 8 | 
            +
             | 
| 9 | 
            +
                # use rspec for tests
         | 
| 10 | 
            +
                config.generators do |g|
         | 
| 11 | 
            +
                  g.test_framework :rspec
         | 
| 12 | 
            +
                end
         | 
| 13 | 
            +
             | 
| 14 | 
            +
                def self.activate
         | 
| 15 | 
            +
                  Dir.glob(File.join(File.dirname(__FILE__), '../../app/**/*_decorator*.rb')) do |c|
         | 
| 16 | 
            +
                    Rails.configuration.cache_classes ? require(c) : load(c)
         | 
| 17 | 
            +
                  end
         | 
| 18 | 
            +
                end
         | 
| 19 | 
            +
             | 
| 20 | 
            +
                config.to_prepare &method(:activate).to_proc
         | 
| 21 | 
            +
              end
         | 
| 22 | 
            +
            end
         | 
| @@ -0,0 +1,6 @@ | |
| 1 | 
            +
            FactoryGirl.define do
         | 
| 2 | 
            +
              # Define your Spree extensions Factories within this file to enable applications, and other extensions to use and override them.
         | 
| 3 | 
            +
              #
         | 
| 4 | 
            +
              # Example adding this to your spec_helper will load these Factories for use:
         | 
| 5 | 
            +
              # require 'spree_account_recurring/factories'
         | 
| 6 | 
            +
            end
         | 
| @@ -0,0 +1,125 @@ | |
| 1 | 
            +
            shared_examples 'ransack_date_search' do |controller_klass, klass, opts|
         | 
| 2 | 
            +
              def send_request(params={q: {}})
         | 
| 3 | 
            +
                spree_get :index, params
         | 
| 4 | 
            +
              end
         | 
| 5 | 
            +
             | 
| 6 | 
            +
              describe 'class_method ransack_date_searchable' do
         | 
| 7 | 
            +
                context 'when options passed in hash' do
         | 
| 8 | 
            +
                  describe 'define and set class attribute' do
         | 
| 9 | 
            +
                    context 'when date_col is passed as option' do
         | 
| 10 | 
            +
                      before(:each) do
         | 
| 11 | 
            +
                        controller_klass.ransack_date_searchable(date_col: opts[:date_col])
         | 
| 12 | 
            +
                      end
         | 
| 13 | 
            +
             | 
| 14 | 
            +
                      it { controller_klass.ransack_date_search_config.should eq({date_col: opts[:date_col]}) }
         | 
| 15 | 
            +
                      it { controller_klass.ransack_date_search_col_ref.should eq(opts[:date_col]) }
         | 
| 16 | 
            +
                      it { controller_klass.ransack_date_search_param_gt.should eq("#{opts[:date_col]}_gt") }
         | 
| 17 | 
            +
                      it { controller_klass.ransack_date_search_param_lt.should eq("#{opts[:date_col]}_lt") }
         | 
| 18 | 
            +
                    end
         | 
| 19 | 
            +
             | 
| 20 | 
            +
                    context 'when date_col is not passed as option' do
         | 
| 21 | 
            +
                      before(:each) do
         | 
| 22 | 
            +
                        controller_klass.ransack_date_searchable
         | 
| 23 | 
            +
                      end
         | 
| 24 | 
            +
             | 
| 25 | 
            +
                      it { controller_klass.ransack_date_search_config.should eq({date_col: 'created_at'}) }
         | 
| 26 | 
            +
                      it { controller_klass.ransack_date_search_col_ref.should eq('created_at') }
         | 
| 27 | 
            +
                      it { controller_klass.ransack_date_search_param_gt.should eq("created_at_gt") }
         | 
| 28 | 
            +
                      it { controller_klass.ransack_date_search_param_lt.should eq("created_at_lt") }
         | 
| 29 | 
            +
                    end
         | 
| 30 | 
            +
                  end
         | 
| 31 | 
            +
                end
         | 
| 32 | 
            +
              end
         | 
| 33 | 
            +
             | 
| 34 | 
            +
              it 'should receive parse_ransack_date_search_param!' do
         | 
| 35 | 
            +
                controller.should_receive(:parse_ransack_date_search_param!)
         | 
| 36 | 
            +
                send_request
         | 
| 37 | 
            +
              end
         | 
| 38 | 
            +
             | 
| 39 | 
            +
              describe '#parse_ransack_date_search_param!' do
         | 
| 40 | 
            +
                let(:time1) { Time.now }
         | 
| 41 | 
            +
                let(:time2) { Time.now - 1.days }
         | 
| 42 | 
            +
                let(:time3) { Time.now + 1.days }
         | 
| 43 | 
            +
             | 
| 44 | 
            +
                before(:each) do
         | 
| 45 | 
            +
                  @ransack_obj = klass.ransack
         | 
| 46 | 
            +
                  Time.stub_chain(:current, :beginning_of_month).and_return(time1)
         | 
| 47 | 
            +
                  Time.stub_chain(:zone, :parse, :beginning_of_day).and_return(time2)
         | 
| 48 | 
            +
                  Time.stub_chain(:zone, :parse, :end_of_day).and_return(time3)
         | 
| 49 | 
            +
                end
         | 
| 50 | 
            +
             | 
| 51 | 
            +
                context 'when params q not present' do
         | 
| 52 | 
            +
                  context 'when params[ransack_date_search_param_gt] present' do
         | 
| 53 | 
            +
                    let(:params) { {q: {"#{opts[:date_col]}_gt" => "11/11/11"}} }
         | 
| 54 | 
            +
             | 
| 55 | 
            +
                    context 'when params[ransack_date_search_param_gt] gives error' do
         | 
| 56 | 
            +
                      before(:each) do
         | 
| 57 | 
            +
                        Time.stub_chain(:zone, :parse, :beginning_of_day).and_raise(StandardError)
         | 
| 58 | 
            +
                      end
         | 
| 59 | 
            +
             | 
| 60 | 
            +
                      it { klass.should_receive(:ransack).with({"#{opts[:date_col]}_gt" => time1, "s"=>"#{opts[:date_col]} desc"}).and_return(@ransack_obj) }
         | 
| 61 | 
            +
                    end
         | 
| 62 | 
            +
             | 
| 63 | 
            +
                    context 'when params[ransack_date_search_param_gt] do not gives error' do
         | 
| 64 | 
            +
                      before(:each) do
         | 
| 65 | 
            +
                        Time.stub_chain(:zone, :parse, :beginning_of_day).and_return(time2)
         | 
| 66 | 
            +
                      end
         | 
| 67 | 
            +
             | 
| 68 | 
            +
                      it { klass.should_receive(:ransack).with({"#{opts[:date_col]}_gt" => time2, "s"=>"#{opts[:date_col]} desc"}).and_return(@ransack_obj) }
         | 
| 69 | 
            +
                    end
         | 
| 70 | 
            +
                  end
         | 
| 71 | 
            +
             | 
| 72 | 
            +
                  context 'when params[ransack_date_search_param_gt] is not present' do
         | 
| 73 | 
            +
                    let(:params) { {q: {}} }
         | 
| 74 | 
            +
             | 
| 75 | 
            +
                    it { klass.should_receive(:ransack).with({"#{opts[:date_col]}_gt" => time1, "s"=>"#{opts[:date_col]} desc"}).and_return(@ransack_obj) }
         | 
| 76 | 
            +
                  end
         | 
| 77 | 
            +
             | 
| 78 | 
            +
                  context 'when params[ransack_date_search_param_lt] present' do
         | 
| 79 | 
            +
                    let(:params) { {q: {"#{opts[:date_col]}_lt" => '14/11/11'}} }
         | 
| 80 | 
            +
             | 
| 81 | 
            +
                    context 'when params[ransack_date_search_param_lt] gives error' do
         | 
| 82 | 
            +
                      before(:each) do
         | 
| 83 | 
            +
                        Time.stub_chain(:zone, :parse, :end_of_day).and_raise(StandardError)
         | 
| 84 | 
            +
                      end
         | 
| 85 | 
            +
             | 
| 86 | 
            +
                      it { klass.should_receive(:ransack).with({"#{opts[:date_col]}_gt" => time1, "s"=>"#{opts[:date_col]} desc"}).and_return(@ransack_obj) }
         | 
| 87 | 
            +
                    end
         | 
| 88 | 
            +
             | 
| 89 | 
            +
                    context 'when params[ransack_date_search_param_lt] do not gives error' do
         | 
| 90 | 
            +
                      before(:each) do
         | 
| 91 | 
            +
                        Time.stub_chain(:zone, :parse, :end_of_day).and_return(time3)
         | 
| 92 | 
            +
                      end
         | 
| 93 | 
            +
             | 
| 94 | 
            +
                      it { klass.should_receive(:ransack).with({"#{opts[:date_col]}_gt" => time1, "#{opts[:date_col]}_lt" => time3, "s"=>"#{opts[:date_col]} desc"}).and_return(@ransack_obj) }
         | 
| 95 | 
            +
                    end
         | 
| 96 | 
            +
                  end
         | 
| 97 | 
            +
             | 
| 98 | 
            +
                  context 'when params[ransack_date_search_param_lt] is not present' do
         | 
| 99 | 
            +
                    let(:params) { {q: {}} }
         | 
| 100 | 
            +
             | 
| 101 | 
            +
                    it { klass.should_receive(:ransack).with({"#{opts[:date_col]}_gt" => time1, "s"=>"#{opts[:date_col]} desc"}).and_return(@ransack_obj) }
         | 
| 102 | 
            +
                  end
         | 
| 103 | 
            +
                end
         | 
| 104 | 
            +
             | 
| 105 | 
            +
                context 'when params[q][s] is present' do
         | 
| 106 | 
            +
                  let(:params) {{q: {s: "#{opts[:date_col]} asc"}}}
         | 
| 107 | 
            +
             | 
| 108 | 
            +
                  it {klass.should_receive(:ransack).with({"#{opts[:date_col]}_gt" => time1, "s"=>"#{opts[:date_col]} asc"}).and_return(@ransack_obj) }
         | 
| 109 | 
            +
                end
         | 
| 110 | 
            +
             | 
| 111 | 
            +
                context 'when params[q][s] is not present' do
         | 
| 112 | 
            +
                  let(:params) {{q: {}}}
         | 
| 113 | 
            +
             | 
| 114 | 
            +
                  it {klass.should_receive(:ransack).with({"#{opts[:date_col]}_gt" => time1, "s"=>"#{opts[:date_col]} desc"}).and_return(@ransack_obj) }
         | 
| 115 | 
            +
                end
         | 
| 116 | 
            +
             | 
| 117 | 
            +
                after(:each) do
         | 
| 118 | 
            +
                  send_request(params)
         | 
| 119 | 
            +
                end
         | 
| 120 | 
            +
              end
         | 
| 121 | 
            +
             | 
| 122 | 
            +
              after(:each) do
         | 
| 123 | 
            +
                controller_klass.ransack_date_searchable(opts)
         | 
| 124 | 
            +
              end
         | 
| 125 | 
            +
            end
         |