spree_promo_user_usage_limit 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 7235d225118aa976d48fb24dc2d8a74664ec23a6
4
+ data.tar.gz: 02ae4c12220a4e61e46686742166ac04de6201a7
5
+ SHA512:
6
+ metadata.gz: 406421fa46f8702dd5c3c3a4015e2230e3608a64786e443debb9f51bd20988068602c1c339384d760a2f3db5baed4b1050a375a53a6902bc10f022b1d6d014a0
7
+ data.tar.gz: 3c3b7f00ea6d9c4b053dfa78e83061266883ceb3e3a44781ddbc57357da149702baaf3b63999e807700ef1d6a52c3b319bca2c50b11aa8762c10869bc3a0e5c2
data/.gitignore ADDED
@@ -0,0 +1,19 @@
1
+ \#*
2
+ *~
3
+ .#*
4
+ .DS_Store
5
+ .idea
6
+ .project
7
+ .sass-cache
8
+ coverage
9
+ Gemfile.lock
10
+ tmp
11
+ nbproject
12
+ pkg
13
+ *.swp
14
+ spec/dummy
15
+ .ruby*
16
+ doc/
17
+ vendor/bundle/
18
+ .bundle/
19
+ bin/
data/.rspec ADDED
@@ -0,0 +1 @@
1
+ --color
data/.travis.yml ADDED
@@ -0,0 +1,21 @@
1
+ before_script:
2
+ - "bundle exec rake test_app"
3
+ script:
4
+ - "bundle exec rspec spec"
5
+ rvm:
6
+ - 1.9.3
7
+ - 2.0.0
8
+ - 2.1
9
+ - jruby-19mode
10
+ - jruby-21mode
11
+ - rbx-2
12
+ env:
13
+ - DB=sqlite
14
+ language: ruby
15
+ matrix:
16
+ allow_failures:
17
+ - rvm: rbx-2
18
+ - rvm: jruby-21mode
19
+ notifications:
20
+ recipients:
21
+ - swrobel@gmail.com
data/CHANGELOG.md ADDED
@@ -0,0 +1,3 @@
1
+ ## 2.0.0, 2.1.0, 2.2.0
2
+
3
+ * Initial release
data/Gemfile ADDED
@@ -0,0 +1,6 @@
1
+ source 'https://rubygems.org'
2
+
3
+ gem 'activerecord-jdbcsqlite3-adapter', platforms: :jruby
4
+ gem 'sqlite3', platforms: :ruby
5
+
6
+ gemspec
data/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2014 Stefan Wrobel
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy of
6
+ this software and associated documentation files (the "Software"), to deal in
7
+ the Software without restriction, including without limitation the rights to
8
+ use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
9
+ the Software, and to permit persons to whom the Software is furnished to do so,
10
+ subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
17
+ FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
18
+ COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
19
+ IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
20
+ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,60 @@
1
+ Spree Promo User Usage Limit
2
+ ======================
3
+ [![Build Status](http://img.shields.io/travis/swrobel/spree_promo_user_usage_limit/2-0-stable.svg)](https://travis-ci.org/swrobel/spree_promo_user_usage_limit) [![Dependency Status](http://img.shields.io/gemnasium/swrobel/spree_promo_user_usage_limit.svg)](https://gemnasium.com/swrobel/spree_promo_user_usage_limit) [![Coverage Status](http://img.shields.io/coveralls/swrobel/spree_promo_user_usage_limit/2-0-stable.svg)](https://coveralls.io/r/swrobel/spree_promo_user_usage_limit) [![Code Climate](http://img.shields.io/codeclimate/github/swrobel/spree_promo_user_usage_limit.svg)](https://codeclimate.com/github/swrobel/spree_promo_user_usage_limit)
4
+
5
+ Adding this rule to a promo will allow you to set a limit on the number of completed orders for which a given user can apply it (default 1 use).
6
+
7
+ ![screenshot](screenshot.png)
8
+
9
+ Installation
10
+ ------------
11
+
12
+ 1. Add spree_promo_user_usage_limit to your Gemfile:
13
+
14
+ ```ruby
15
+ gem 'spree_promo_user_usage_limit'
16
+ ```
17
+
18
+ 1. Bundle your dependencies:
19
+
20
+ ```shell
21
+ bundle
22
+ ```
23
+
24
+ 1. Add this rule to a promo and set the number of uses you want to allow
25
+
26
+ 1. Profit.
27
+
28
+ Versioning
29
+ ----------
30
+ Versions files the pattern MAJOR.MINOR.PATCH [SemVer-style](http://semver.org/). MAJOR.MINOR version will always match the Spree version that gem is compatible with. PATCH version is incremented as new bugfix releases of this gem come out, indepently of new Spree PATCH versions.
31
+
32
+ For example, version 2.1.0 is compatible with the Spree 2.1.x series, while version 2.0.0 is compatible with the Spree 2.0.x series.
33
+
34
+ You should not need to worry about this, as the gemspec has the appropriate constraints. But hey, the more you know.
35
+
36
+ Testing
37
+ -------
38
+ This extension is tested against the following rubies:
39
+
40
+ * 1.9.3
41
+ * 2.0
42
+ * 2.1
43
+ * jruby-19mode
44
+ * jruby-21mode (experimental)
45
+ * rubinius (experimental)
46
+
47
+ ### Running the tests locally
48
+
49
+ Be sure to bundle your dependencies and then create a dummy test app for the specs to run against.
50
+
51
+ ```shell
52
+ bundle
53
+ bundle exec rake test_app
54
+ bundle exec rspec spec
55
+ ```
56
+
57
+ License
58
+ -------
59
+
60
+ Copyright (c) 2014 Stefan Wrobel, released under the MIT License
data/Rakefile ADDED
@@ -0,0 +1,21 @@
1
+ require 'bundler'
2
+ Bundler::GemHelper.install_tasks
3
+
4
+ require 'rspec/core/rake_task'
5
+ require 'spree/testing_support/extension_rake'
6
+
7
+ RSpec::Core::RakeTask.new
8
+
9
+ task :default do
10
+ if Dir["spec/dummy"].empty?
11
+ Rake::Task[:test_app].invoke
12
+ Dir.chdir("../../")
13
+ end
14
+ Rake::Task[:spec].invoke
15
+ end
16
+
17
+ desc 'Generates a dummy app for testing'
18
+ task :test_app do
19
+ ENV['LIB_NAME'] = 'spree_promo_user_usage_limit'
20
+ Rake::Task['extension:test_app'].invoke
21
+ end
data/Versionfile ADDED
@@ -0,0 +1,15 @@
1
+ # This file is used to designate compatibilty with different versions of Spree
2
+ # Please see http://spreecommerce.com/documentation/extensions.html#versionfile for details
3
+
4
+ # Examples
5
+ #
6
+ # '1.2.x' => { :branch => 'master' }
7
+ # '1.1.x' => { :branch => '1-1-stable' }
8
+ # '1.0.x' => { :branch => '1-0-stable' }
9
+ # '0.70.x' => { :branch => '0-70-stable' }
10
+ # '0.40.x' => { :tag => 'v1.0.0', :version => '1.0.0' }
11
+
12
+ "2.3.x" => { :branch => "master" }
13
+ "2.2.x" => { :branch => "2-2-stable" }
14
+ "2.1.x" => { :branch => "2-1-stable" }
15
+ "2.0.x" => { :branch => "2-0-stable" }
@@ -0,0 +1,30 @@
1
+ # A rule to restrict a promotion to N uses per user
2
+ module Spree
3
+ class Promotion
4
+ module Rules
5
+ class UserUsageLimit < PromotionRule
6
+ preference :uses, :integer, default: 1
7
+
8
+ attr_accessible :preferred_uses
9
+
10
+ def applicable?(promotable)
11
+ promotable.is_a?(Spree::Order)
12
+ end
13
+
14
+ def eligible?(order, options = {})
15
+ if order.user
16
+ order_ids = order.user.orders.complete.pluck(:id)
17
+ elsif order.email
18
+ order_ids = Spree::Order.complete.where(email: order.email).pluck(:id)
19
+ else # user or email required to check against previous orders
20
+ return false
21
+ end
22
+ action_ids = promotion.actions.pluck(:id)
23
+ promotion_count = Spree::Adjustment.promotion.where(adjustable_id: order_ids).where(originator_id: action_ids).count
24
+
25
+ promotion_count < preferred_uses
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,5 @@
1
+ <div class="field alpha omega eight columns">
2
+ <label>
3
+ <%= Spree.t('user_usage_limit.label', input: text_field_tag("#{param_prefix}[preferred_uses]", promotion_rule.preferred_uses, style: 'width: 40px;')).html_safe %>
4
+ </label>
5
+ </div>
@@ -0,0 +1,8 @@
1
+ en:
2
+ spree:
3
+ promotion_rule_types:
4
+ user_usage_limit:
5
+ description: Can be used a limited number of times per user.
6
+ name: User usage limit
7
+ user_usage_limit:
8
+ label: Can only be used %{input} times per user
data/config/routes.rb ADDED
@@ -0,0 +1,3 @@
1
+ Spree::Core::Engine.routes.draw do
2
+ # Add your extension routes here
3
+ end
@@ -0,0 +1,25 @@
1
+ module SpreePromoUserUsageLimit
2
+ class Engine < Rails::Engine
3
+ require 'spree/core'
4
+ isolate_namespace Spree
5
+ engine_name 'spree_promo_user_usage_limit'
6
+
7
+ # use rspec for tests
8
+ config.generators do |g|
9
+ g.test_framework :rspec
10
+ end
11
+
12
+ def self.activate
13
+ Dir.glob(File.join(File.dirname(__FILE__), '../../app/**/*_decorator*.rb')) do |c|
14
+ Rails.configuration.cache_classes ? require(c) : load(c)
15
+ end
16
+ end
17
+
18
+ config.to_prepare &method(:activate).to_proc
19
+
20
+ initializer "spree_promo_user_usage_limit.register.promotion_rules" do |app|
21
+ app.config.spree.promotions.rules << Spree::Promotion::Rules::UserUsageLimit
22
+
23
+ end
24
+ end
25
+ 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_promo_user_usage_limit/factories'
6
+ end
@@ -0,0 +1,2 @@
1
+ require 'spree_core'
2
+ require 'spree_promo_user_usage_limit/engine'
data/screenshot.png ADDED
Binary file
@@ -0,0 +1,74 @@
1
+ require 'spec_helper'
2
+
3
+ describe Spree::Promotion::Rules::UserUsageLimit do
4
+ let(:user) { create(:user) }
5
+ let(:promotion) { create(:promotion) }
6
+ let(:rule) { Spree::Promotion::Rules::UserUsageLimit.create }
7
+
8
+ before do
9
+ promotion.rules << rule
10
+ promotion.actions << Spree::Promotion::Actions::CreateAdjustment.new
11
+ end
12
+
13
+ describe "#applicable?" do
14
+ context "with an order" do
15
+ let(:order) { mock_model(Spree::Order, :user => nil, :email => nil) }
16
+
17
+ it { rule.should be_applicable(order) }
18
+ end
19
+
20
+ context "with a promotion" do
21
+ it { rule.should_not be_applicable(promotion) }
22
+ end
23
+ end
24
+
25
+ context "without a user or guest email" do
26
+ let(:order) { mock_model(Spree::Order, :user => nil, :email => nil) }
27
+
28
+ it { rule.should_not be_eligible(order) }
29
+ end
30
+
31
+ context "for a signed user" do
32
+ context "with no completed orders" do
33
+ let(:order) { mock_model(Spree::Order, :user => user) }
34
+
35
+ it { rule.should be_eligible(order) }
36
+ end
37
+
38
+ context "with a completed order" do
39
+ let(:order) { create(:completed_order_with_totals, user: user) }
40
+
41
+ context "that didn't use the promo" do
42
+ it { rule.should be_eligible(order) }
43
+ end
44
+
45
+ context "that used the promo" do
46
+ before { create(:adjustment, adjustable: order, source: order, originator: promotion.actions.first) }
47
+
48
+ it { rule.should_not be_eligible(order) }
49
+ end
50
+ end
51
+
52
+ context "with an incomplete order that used the promo" do
53
+ let(:order) { create(:order_with_totals, user: user) }
54
+ before { create(:adjustment, adjustable: order, source: order, originator: promotion.actions.first) }
55
+
56
+ it { rule.should be_eligible(order) }
57
+ end
58
+ end
59
+
60
+ context "for a guest user" do
61
+ let(:email) { 'user@spreecommerce.com' }
62
+ let(:order) { create(:completed_order_with_totals, email: email) }
63
+
64
+ context "with no other orders" do
65
+ it { rule.should be_eligible(order) }
66
+ end
67
+
68
+ context "with another order" do
69
+ before { create(:adjustment, adjustable: order, source: order, originator: promotion.actions.first) }
70
+
71
+ it { rule.should_not be_eligible(order) }
72
+ end
73
+ end
74
+ end
@@ -0,0 +1,57 @@
1
+ # Run Coverage report
2
+ require 'simplecov'
3
+ require 'coveralls'
4
+ SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter[
5
+ SimpleCov::Formatter::HTMLFormatter,
6
+ Coveralls::SimpleCov::Formatter
7
+ ]
8
+ SimpleCov.start do
9
+ add_filter 'spec/dummy'
10
+ add_filter 'vendor'
11
+ add_filter 'bin'
12
+ add_group 'Controllers', 'app/controllers'
13
+ add_group 'Helpers', 'app/helpers'
14
+ add_group 'Mailers', 'app/mailers'
15
+ add_group 'Models', 'app/models'
16
+ add_group 'Views', 'app/views'
17
+ add_group 'Libraries', 'lib'
18
+ end
19
+
20
+ # Configure Rails Environment
21
+ ENV['RAILS_ENV'] = 'test'
22
+
23
+ require File.expand_path('../dummy/config/environment.rb', __FILE__)
24
+
25
+ require 'rspec/rails'
26
+ require 'ffaker'
27
+
28
+ # Requires supporting ruby files with custom matchers and macros, etc,
29
+ # in spec/support/ and its subdirectories.
30
+ Dir[File.join(File.dirname(__FILE__), 'support/**/*.rb')].each { |f| require f }
31
+
32
+ # Requires factories defined in spree_core
33
+ require 'spree/testing_support/factories'
34
+
35
+ # Requires factories defined in lib/spree_promo_user_usage_limit/factories.rb
36
+ require 'spree_promo_user_usage_limit/factories'
37
+
38
+ RSpec.configure do |config|
39
+ config.include FactoryGirl::Syntax::Methods
40
+
41
+ # == Mock Framework
42
+ #
43
+ # If you prefer to use mocha, flexmock or RR, uncomment the appropriate line:
44
+ #
45
+ # config.mock_with :mocha
46
+ # config.mock_with :flexmock
47
+ # config.mock_with :rr
48
+ config.mock_with :rspec
49
+ config.color = true
50
+
51
+ # Remove this line if you're not using ActiveRecord or ActiveRecord fixtures
52
+ config.fixture_path = "#{::Rails.root}/spec/fixtures"
53
+
54
+ config.use_transactional_fixtures = true
55
+
56
+ config.fail_fast = ENV['FAIL_FAST'] || false
57
+ end
@@ -0,0 +1,27 @@
1
+ # encoding: UTF-8
2
+ Gem::Specification.new do |s|
3
+ s.platform = Gem::Platform::RUBY
4
+ s.name = 'spree_promo_user_usage_limit'
5
+ s.version = '2.0.0'
6
+ s.summary = 'Allow each user to use a promotion a maximum of N times'
7
+ s.description = 'Adding this rule to a promo will allow you to set a limit on the number of completed orders for which a given user can apply it (default 1 use).'
8
+ s.required_ruby_version = '>= 1.9.3'
9
+
10
+ s.author = 'Stefan Wrobel'
11
+ s.email = 'swrobel@gmail.com'
12
+ s.homepage = 'https://github.com/swrobel/spree_promo_user_usage_limit'
13
+ s.license = 'MIT'
14
+
15
+ s.files = `git ls-files`.split("\n")
16
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
17
+ s.require_path = 'lib'
18
+ s.requirements << 'none'
19
+
20
+ s.add_dependency 'spree_core', '~> 2.0.0'
21
+
22
+ s.add_development_dependency 'factory_girl', '~> 4.4'
23
+ s.add_development_dependency 'ffaker'
24
+ s.add_development_dependency 'rspec-rails', '~> 2.13'
25
+ s.add_development_dependency 'simplecov'
26
+ s.add_development_dependency 'coveralls'
27
+ end
metadata ADDED
@@ -0,0 +1,151 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: spree_promo_user_usage_limit
3
+ version: !ruby/object:Gem::Version
4
+ version: 2.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Stefan Wrobel
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-06-12 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: spree_core
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: 2.0.0
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: 2.0.0
27
+ - !ruby/object:Gem::Dependency
28
+ name: factory_girl
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '4.4'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '4.4'
41
+ - !ruby/object:Gem::Dependency
42
+ name: ffaker
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ - !ruby/object:Gem::Dependency
56
+ name: rspec-rails
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: '2.13'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: '2.13'
69
+ - !ruby/object:Gem::Dependency
70
+ name: simplecov
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ version: '0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ">="
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: coveralls
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">="
88
+ - !ruby/object:Gem::Version
89
+ version: '0'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: '0'
97
+ description: Adding this rule to a promo will allow you to set a limit on the number
98
+ of completed orders for which a given user can apply it (default 1 use).
99
+ email: swrobel@gmail.com
100
+ executables: []
101
+ extensions: []
102
+ extra_rdoc_files: []
103
+ files:
104
+ - ".gitignore"
105
+ - ".rspec"
106
+ - ".travis.yml"
107
+ - CHANGELOG.md
108
+ - Gemfile
109
+ - LICENSE
110
+ - README.md
111
+ - Rakefile
112
+ - Versionfile
113
+ - app/models/spree/promotion/rules/user_usage_limit.rb
114
+ - app/views/spree/admin/promotions/rules/_user_usage_limit.html.erb
115
+ - config/locales/en.yml
116
+ - config/routes.rb
117
+ - lib/spree_promo_user_usage_limit.rb
118
+ - lib/spree_promo_user_usage_limit/engine.rb
119
+ - lib/spree_promo_user_usage_limit/factories.rb
120
+ - screenshot.png
121
+ - spec/models/spree/promotion/rules/user_usage_limit_spec.rb
122
+ - spec/spec_helper.rb
123
+ - spree_promo_user_usage_limit.gemspec
124
+ homepage: https://github.com/swrobel/spree_promo_user_usage_limit
125
+ licenses:
126
+ - MIT
127
+ metadata: {}
128
+ post_install_message:
129
+ rdoc_options: []
130
+ require_paths:
131
+ - lib
132
+ required_ruby_version: !ruby/object:Gem::Requirement
133
+ requirements:
134
+ - - ">="
135
+ - !ruby/object:Gem::Version
136
+ version: 1.9.3
137
+ required_rubygems_version: !ruby/object:Gem::Requirement
138
+ requirements:
139
+ - - ">="
140
+ - !ruby/object:Gem::Version
141
+ version: '0'
142
+ requirements:
143
+ - none
144
+ rubyforge_project:
145
+ rubygems_version: 2.2.2
146
+ signing_key:
147
+ specification_version: 4
148
+ summary: Allow each user to use a promotion a maximum of N times
149
+ test_files:
150
+ - spec/models/spree/promotion/rules/user_usage_limit_spec.rb
151
+ - spec/spec_helper.rb