aasm 4.5.0 → 4.6.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 92b6a0df28245debe06c0ecbd3bd95e91b0cf323
4
- data.tar.gz: 99bfa6652b17a26388b073ee431a1878ce961a4e
3
+ metadata.gz: 5b8d8a7ce2210a49761c9f1c622393a1bc453452
4
+ data.tar.gz: 1239b8468c521eb11bdbfef04d58540a6d1e5b72
5
5
  SHA512:
6
- metadata.gz: d6cf5a7eea74d1c20108d48370d0f6048722efefb6af0110c70de56dd13032bcaabf57749add95ae25dc086faab8cbb5dcf9ad08ad4cafbafdfb400481ce1fd4
7
- data.tar.gz: 90a92ba66f2b4d67c898a9076f324e0c99ce768aa5160f6d70dc74bca48e8ba4cf95317bf5e203b66985e9dcd77a52fb814dc65cc45f498dfeab20fde31fecb8
6
+ metadata.gz: 7b8f2affa363cce45636f684c24e2f72d71cb0a5af4fce0303894a77eb9db7fb37f08442c4b4b1955d7aaae042225ec4b3e52b27ffafe5cbb0c765c15498cf65
7
+ data.tar.gz: d9769d7cfd98b28e98f8a79c9b0b823cabec8b721bf5bdfaaae3dac37ca2b6127c38b42d427ed2fd451a67987c2371e36f4b46df09e0b4042fb1abb2c44320cd
data/.gitignore CHANGED
@@ -17,3 +17,4 @@ alto
17
17
  .rspec
18
18
  .bundle
19
19
  tags
20
+ tmp
data/.travis.yml CHANGED
@@ -11,12 +11,13 @@ rvm:
11
11
  - 2.2
12
12
  # - jruby-18mode # JRuby in 1.8 mode
13
13
  - jruby-1.7 # JRuby in 1.9 mode
14
+ - jruby-9.0.3.0
14
15
  - rbx-2.2.1
15
16
 
16
17
  services: mongodb
17
18
 
18
19
  gemfile:
19
- - gemfiles/rails_3.2.gemfile
20
+ - gemfiles/rails_3.2_stable.gemfile
20
21
  - gemfiles/rails_4.0.gemfile
21
22
  - gemfiles/rails_4.0_mongo_mapper.gemfile
22
23
  - gemfiles/rails_4.1.gemfile
data/CHANGELOG.md CHANGED
@@ -1,5 +1,18 @@
1
1
  # CHANGELOG
2
2
 
3
+ ## 4.6.0
4
+
5
+ * fix: make sure the column is actually present for _ActiveRecord_ enums (see [issue #265](https://github.com/aasm/aasm/issues/265) and [issue #152](https://github.com/aasm/aasm/issues/152) for details, thanks to [@anilmaurya](https://github.com/anilmaurya))
6
+ * add generators to configure active_record and mongoid after install (see [issue #261](https://github.com/aasm/aasm/issues/261) for details, thanks to [@anilmaurya](https://github.com/anilmaurya))
7
+
8
+ ## 4.5.2
9
+
10
+ * fix arity difference between Procs and lambdas (see [issue #293](https://github.com/aasm/aasm/issues/293) for details)
11
+
12
+ ## 4.5.1
13
+
14
+ * make sure to use override configuration options if state machine is defined more than once (see [issue #287](https://github.com/aasm/aasm/issues/287) for details)
15
+
3
16
  ## 4.5.0
4
17
 
5
18
  * add RSpec matchers `have_state`, `allow_event` and `allow_transition_to` (see [issue #147](https://github.com/aasm/aasm/issues/147) for details)
data/LICENSE CHANGED
@@ -1,4 +1,4 @@
1
- Copyright (c) 2006-2015 Scott Barron
1
+ Copyright (c) 2006-2016 Scott Barron
2
2
 
3
3
  Permission is hereby granted, free of charge, to any person obtaining
4
4
  a copy of this software and associated documentation files (the
data/README.md CHANGED
@@ -615,7 +615,7 @@ callback or the state update fails, all changes to any database record are rolle
615
615
  Mongodb does not support transactions.
616
616
 
617
617
  If you want to make sure a depending action happens only after the transaction is committed,
618
- use the `after_commit` callback, like this:
618
+ use the `after_commit` callback along with the auto-save (bang) methods, like this:
619
619
 
620
620
  ```ruby
621
621
  class Job < ActiveRecord::Base
@@ -634,6 +634,18 @@ class Job < ActiveRecord::Base
634
634
  ...
635
635
  end
636
636
  end
637
+
638
+ job = Job.where(state: 'sleeping').first!
639
+ job.run! # Saves the model and triggers the after_commit callback
640
+ ```
641
+
642
+ Note that the following will not run the `after_commit` callbacks because
643
+ the auto-save method is not used:
644
+
645
+ ```ruby
646
+ job = Job.where(state: 'sleeping').first!
647
+ job.run
648
+ job.save! #notify_about_running_job is not run
637
649
  ```
638
650
 
639
651
  If you want to encapsulate state changes within an own transaction, the behavior
@@ -779,6 +791,17 @@ gem 'aasm'
779
791
  % sudo gem install pkg/aasm-x.y.z.gem
780
792
  ```
781
793
 
794
+ ### Generators
795
+
796
+ After installing Aasm you can run generator:
797
+
798
+ ```sh
799
+ % rails generate aasm NAME [COLUMN_NAME]
800
+ ```
801
+ Replace NAME with the Model name, COLUMN_NAME is optional(default is 'aasm_state').
802
+ This will create a model (if one does not exist) and configure it with aasm block.
803
+ For Active record orm a migration file is added to add aasm state column to table.
804
+
782
805
  ## Latest changes ##
783
806
 
784
807
  Take a look at the [CHANGELOG](https://github.com/aasm/aasm/blob/master/CHANGELOG.md) for details about recent changes to the current version.
@@ -816,7 +839,7 @@ purpose.
816
839
 
817
840
  ## License ##
818
841
 
819
- Copyright (c) 2006-2015 Scott Barron
842
+ Copyright (c) 2006-2016 Scott Barron
820
843
 
821
844
  Permission is hereby granted, free of charge, to any person obtaining
822
845
  a copy of this software and associated documentation files (the
data/aasm.gemspec CHANGED
@@ -19,6 +19,7 @@ Gem::Specification.new do |s|
19
19
  s.add_development_dependency 'rake'
20
20
  s.add_development_dependency 'sdoc'
21
21
  s.add_development_dependency 'rspec', ">= 3"
22
+ s.add_development_dependency 'generator_spec'
22
23
 
23
24
  # debugging
24
25
  # s.add_development_dependency 'debugger'
@@ -5,10 +5,11 @@ gem 'rubysl', :platforms => :rbx
5
5
  gem 'rubinius-developer_tools', :platforms => :rbx
6
6
  gem "jruby-openssl", :platforms => :jruby
7
7
  gem "activerecord-jdbcsqlite3-adapter", :platforms => :jruby
8
- gem "rails", "3.2.21"
8
+ gem "rails", :github => "rails/rails", :branch => "3-2-stable"
9
9
  gem 'mongoid', '~>3.1' if Gem::Version.create(RUBY_VERSION.dup) >= Gem::Version.create('1.9.3')
10
10
  gem 'sequel'
11
11
  gem 'mongo_mapper', '~>0.13'
12
12
  gem 'bson_ext', :platforms => :ruby
13
+ gem 'test-unit', '~> 3.0'
13
14
 
14
15
  gemspec :path => "../"
data/lib/aasm/aasm.rb CHANGED
@@ -39,7 +39,20 @@ module AASM
39
39
  AASM::StateMachine[self][state_machine_name] ||= AASM::StateMachine.new(state_machine_name)
40
40
 
41
41
  @aasm ||= {}
42
- @aasm[state_machine_name] ||= AASM::Base.new(self, state_machine_name, AASM::StateMachine[self][state_machine_name], options)
42
+ if @aasm[state_machine_name]
43
+ # make sure to use provided options
44
+ options.each do |key, value|
45
+ @aasm[state_machine_name].state_machine.config.send("#{key}=", value)
46
+ end
47
+ else
48
+ # create a new base
49
+ @aasm[state_machine_name] = AASM::Base.new(
50
+ self,
51
+ state_machine_name,
52
+ AASM::StateMachine[self][state_machine_name],
53
+ options
54
+ )
55
+ end
43
56
  @aasm[state_machine_name].instance_eval(&block) if block # new DSL
44
57
  @aasm[state_machine_name]
45
58
  end
@@ -55,7 +55,7 @@ module AASM::Core
55
55
  arity = record.send(:method, code.to_sym).arity
56
56
  arity == 0 ? record.send(code) : record.send(code, *args)
57
57
  when Proc
58
- code.arity == 0 ? record.instance_exec(&code) : record.instance_exec(*args, &code)
58
+ code.parameters.size == 0 ? record.instance_exec(&code) : record.instance_exec(*args, &code)
59
59
  when Array
60
60
  if options[:guard]
61
61
  # invoke guard callbacks
@@ -57,16 +57,12 @@ module AASM
57
57
 
58
58
  success = if aasm_skipping_validations(name)
59
59
  value = aasm_raw_attribute_value(state, name)
60
- self.class.where(self.class.primary_key => self.id).update_all(self.class.aasm(name).attribute_name => value) == 1
60
+ aasm_update_column(name, value)
61
61
  else
62
62
  self.save
63
63
  end
64
- unless success
65
- write_attribute(self.class.aasm(name).attribute_name, old_value)
66
- return false
67
- end
68
64
 
69
- true
65
+ success ? true : aasm_rollback(name, old_value)
70
66
  end
71
67
 
72
68
  # Writes <tt>state</tt> to the state column, but does not persist it to the database
@@ -86,6 +82,16 @@ module AASM
86
82
  end
87
83
 
88
84
  private
85
+
86
+ def aasm_update_column(name, value)
87
+ self.class.where(self.class.primary_key => self.id).update_all(self.class.aasm(name).attribute_name => value) == 1
88
+ end
89
+
90
+ def aasm_rollback(name, old_value)
91
+ write_attribute(self.class.aasm(name).attribute_name, old_value)
92
+ false
93
+ end
94
+
89
95
  def aasm_enum(name=:default)
90
96
  case AASM::StateMachine[self.class][name].config.enum
91
97
  when false then nil
@@ -96,7 +102,10 @@ module AASM
96
102
  end
97
103
 
98
104
  def aasm_column_looks_like_enum(name=:default)
99
- self.class.columns_hash[self.class.aasm(name).attribute_name.to_s].type == :integer
105
+ column_name = self.class.aasm(name).attribute_name.to_s
106
+ column = self.class.columns_hash[column_name]
107
+ raise NoMethodError.new("undefined method '#{column_name}' for #{self.class}") if column.nil?
108
+ column.type == :integer
100
109
  end
101
110
 
102
111
  def aasm_guess_enum_method(name=:default)
@@ -120,7 +129,7 @@ module AASM
120
129
  end
121
130
 
122
131
  # Ensures that if the aasm_state column is nil and the record is new
123
- # that the initial state gets populated before validation on create
132
+ # then the initial state gets populated before validation on create
124
133
  #
125
134
  # foo = Foo.new
126
135
  # foo.aasm_state # => nil
@@ -138,12 +147,17 @@ module AASM
138
147
  AASM::StateMachine[self.class].keys.each do |state_machine_name|
139
148
  # checking via respond_to? does not work in Rails <= 3
140
149
  # if respond_to?(self.class.aasm(state_machine_name).attribute_name) && send(self.class.aasm(state_machine_name).attribute_name).blank? # Rails 4
141
- if attribute_names.include?(self.class.aasm(state_machine_name).attribute_name.to_s) && send(self.class.aasm(state_machine_name).attribute_name).blank?
150
+ if aasm_column_is_blank?(state_machine_name)
142
151
  aasm(state_machine_name).enter_initial_state
143
152
  end
144
153
  end
145
154
  end
146
155
 
156
+ def aasm_column_is_blank?(state_machine_name)
157
+ attribute_name = self.class.aasm(state_machine_name).attribute_name
158
+ attribute_names.include?(attribute_name.to_s) && send(attribute_name).blank?
159
+ end
160
+
147
161
  def aasm_fire_event(state_machine_name, name, options, *args, &block)
148
162
  success = options[:persist] ? self.class.transaction(:requires_new => requires_new?(state_machine_name)) { super } : super
149
163
 
@@ -162,12 +176,16 @@ module AASM
162
176
  def aasm_validate_states
163
177
  AASM::StateMachine[self.class].keys.each do |state_machine_name|
164
178
  unless aasm_skipping_validations(state_machine_name)
165
- if aasm(state_machine_name).current_state && !aasm(state_machine_name).states.include?(aasm(state_machine_name).current_state)
179
+ if aasm_invalid_state?(state_machine_name)
166
180
  self.errors.add(AASM::StateMachine[self.class][state_machine_name].config.column , "is invalid")
167
181
  end
168
182
  end
169
183
  end
170
184
  end
185
+
186
+ def aasm_invalid_state?(state_machine_name)
187
+ aasm(state_machine_name).current_state && !aasm(state_machine_name).states.include?(aasm(state_machine_name).current_state)
188
+ end
171
189
  end # InstanceMethods
172
190
 
173
191
  end
@@ -55,35 +55,62 @@ module AASM
55
55
  # make sure to create a (named) scope for each state
56
56
  def state_with_scope(name, *args)
57
57
  state_without_scope(name, *args)
58
- if @state_machine.config.create_scopes && !@klass.respond_to?(name)
58
+ create_scope(name) if create_scope?(name)
59
+ end
60
+ alias_method :state_without_scope, :state
61
+ alias_method :state, :state_with_scope
59
62
 
60
- if @klass.ancestors.map {|klass| klass.to_s}.include?("ActiveRecord::Base")
61
- conditions = {"#{@klass.table_name}.#{@klass.aasm(@name).attribute_name}" => name.to_s}
62
- if ActiveRecord::VERSION::MAJOR >= 3
63
- @klass.class_eval do
64
- scope name, lambda { where(conditions) }
65
- end
66
- else
67
- @klass.class_eval do
68
- named_scope name, :conditions => conditions
69
- end
70
- end
71
- elsif @klass.ancestors.map {|klass| klass.to_s}.include?("Mongoid::Document")
72
- klass = @klass
73
- state_machine_name = @name
74
- scope_options = lambda {
75
- klass.send(:where, {klass.aasm(state_machine_name).attribute_name.to_sym => name.to_s})
76
- }
77
- @klass.send(:scope, name, scope_options)
78
- elsif @klass.ancestors.map {|klass| klass.to_s}.include?("MongoMapper::Document")
79
- conditions = { @klass.aasm(@name).attribute_name.to_sym => name.to_s }
80
- @klass.scope(name, lambda { @klass.where(conditions) })
81
- end
63
+ private
64
+
65
+ def create_scope?(name)
66
+ @state_machine.config.create_scopes && !@klass.respond_to?(name)
67
+ end
82
68
 
69
+ def create_scope(name)
70
+ if ancestors_include?("ActiveRecord::Base")
71
+ create_for_active_record(name)
72
+ elsif ancestors_include?("Mongoid::Document")
73
+ create_for_mongoid(name)
74
+ elsif ancestors_include?("MongoMapper::Document")
75
+ create_for_mongomapper(name)
83
76
  end
84
77
  end
85
- alias_method :state_without_scope, :state
86
- alias_method :state, :state_with_scope
78
+
79
+ def ancestors_include?(class_name)
80
+ @klass.ancestors.map { |klass| klass.to_s }.include?(class_name)
81
+ end
82
+
83
+ def create_for_active_record(name)
84
+ conditions = {
85
+ "#{@klass.table_name}.#{@klass.aasm(@name).attribute_name}" => name.to_s
86
+ }
87
+ if ActiveRecord::VERSION::MAJOR >= 3
88
+ @klass.class_eval do
89
+ scope name, lambda { where(conditions) }
90
+ end
91
+ else
92
+ @klass.class_eval do
93
+ named_scope name, :conditions => conditions
94
+ end
95
+ end
96
+ end
97
+
98
+ def create_for_mongoid(name)
99
+ klass = @klass
100
+ state_machine_name = @name
101
+ scope_options = lambda {
102
+ klass.send(
103
+ :where,
104
+ { klass.aasm(state_machine_name).attribute_name.to_sym => name.to_s }
105
+ )
106
+ }
107
+ @klass.send(:scope, name, scope_options)
108
+ end
109
+
110
+ def create_for_mongomapper(name)
111
+ conditions = { @klass.aasm(@name).attribute_name.to_sym => name.to_s }
112
+ @klass.scope(name, lambda { @klass.where(conditions) })
113
+ end
87
114
  end # Base
88
115
 
89
116
  end # AASM
data/lib/aasm/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module AASM
2
- VERSION = "4.5.0"
2
+ VERSION = "4.6.0"
3
3
  end
@@ -0,0 +1,17 @@
1
+ require 'rails/generators/named_base'
2
+
3
+ module AASM
4
+ module Generators
5
+ class AASMGenerator < Rails::Generators::NamedBase
6
+
7
+ source_root File.expand_path("../templates", __FILE__)
8
+ argument :column_name, type: :string, default: 'aasm_state'
9
+
10
+ desc "Generates a model with the given NAME (if one does not exist) with aasm " <<
11
+ "block and migration to add aasm_state column."
12
+
13
+ hook_for :orm
14
+
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,35 @@
1
+ module AASM
2
+ module Generators
3
+ module OrmHelpers
4
+
5
+ def model_contents
6
+ if column_name == 'aasm_state'
7
+ <<RUBY
8
+ include AASM
9
+
10
+ aasm do
11
+ end
12
+ RUBY
13
+ else
14
+ <<RUBY
15
+ include AASM
16
+
17
+ aasm :column => '#{column_name}' do
18
+ end
19
+ RUBY
20
+ end
21
+ end
22
+
23
+ private
24
+
25
+ def model_exists?
26
+ File.exists?(File.join(destination_root, model_path))
27
+ end
28
+
29
+ def model_path
30
+ @model_path ||= File.join("app", "models", "#{file_path}.rb")
31
+ end
32
+
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,38 @@
1
+ require 'rails/generators/active_record'
2
+ require 'generators/aasm/orm_helpers'
3
+
4
+ module ActiveRecord
5
+ module Generators
6
+ class AASMGenerator < ActiveRecord::Generators::Base
7
+ include AASM::Generators::OrmHelpers
8
+
9
+ argument :column_name, type: :string, default: 'aasm_state'
10
+
11
+ source_root File.expand_path("../templates", __FILE__)
12
+
13
+ def copy_aasm_migration
14
+ if model_exists?
15
+ migration_template "migration_existing.rb", "db/migrate/add_aasm_state_to_#{table_name}.rb"
16
+ else
17
+ migration_template "migration.rb", "db/migrate/aasm_create_#{table_name}.rb"
18
+ end
19
+ end
20
+
21
+ def generate_model
22
+ invoke "active_record:model", [name], migration: false unless model_exists?
23
+ end
24
+
25
+ def inject_aasm_content
26
+ content = model_contents
27
+
28
+ class_path = if namespaced?
29
+ class_name.to_s.split("::")
30
+ else
31
+ [class_name]
32
+ end
33
+ inject_into_class(model_path, class_path.last, content) if model_exists?
34
+ end
35
+
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,8 @@
1
+ class AASMCreate<%= table_name.camelize %> < ActiveRecord::Migration
2
+ def change
3
+ create_table(:<%= table_name %>) do |t|
4
+ t.string :<%= column_name %>
5
+ t.timestamps null: false
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,9 @@
1
+ class AddAASMTo<%= table_name.camelize %> < ActiveRecord::Migration
2
+ def self.up
3
+ add_column :<%= table_name %>, :<%= column_name %>, :string
4
+ end
5
+
6
+ def self.down
7
+ remove_column :<%= table_name %>, :<%= column_name %>
8
+ end
9
+ end
@@ -0,0 +1,28 @@
1
+ require 'rails/generators/named_base'
2
+ require 'generators/aasm/orm_helpers'
3
+
4
+ module Mongoid
5
+ module Generators
6
+ class AASMGenerator < Rails::Generators::NamedBase
7
+ include AASM::Generators::OrmHelpers
8
+
9
+ argument :column_name, type: :string, default: 'aasm_state'
10
+
11
+ def generate_model
12
+ invoke "mongoid:model", [name] unless model_exists?
13
+ end
14
+
15
+ def inject_aasm_content
16
+ inject_into_file model_path, model_contents, after: "include Mongoid::Document\n" if model_exists?
17
+ end
18
+
19
+ def inject_field_types
20
+ inject_into_file model_path, migration_data, after: "include Mongoid::Document\n" if model_exists?
21
+ end
22
+
23
+ def migration_data
24
+ " field :#{column_name}"
25
+ end
26
+ end
27
+ end
28
+ end
data/spec/database.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  ActiveRecord::Migration.suppress_messages do
2
- %w{gates multiple_gates readers writers transients simples no_scopes multiple_no_scopes no_direct_assignments multiple_no_direct_assignments thieves multiple_thieves localizer_test_models persisted_states provided_and_persisted_states with_enums with_true_enums with_false_enums false_states multiple_with_enums multiple_with_true_enums multiple_with_false_enums multiple_false_states readme_jobs}.each do |table_name|
2
+ %w{gates multiple_gates readers writers transients simples no_scopes multiple_no_scopes no_direct_assignments multiple_no_direct_assignments thieves multiple_thieves localizer_test_models persisted_states provided_and_persisted_states with_enums with_enum_without_columns multiple_with_enum_without_columns with_true_enums with_false_enums false_states multiple_with_enums multiple_with_true_enums multiple_with_false_enums multiple_false_states readme_jobs}.each do |table_name|
3
3
  ActiveRecord::Migration.create_table table_name, :force => true do |t|
4
4
  t.string "aasm_state"
5
5
  end
@@ -0,0 +1,39 @@
1
+ require 'spec_helper'
2
+ require 'generator_spec'
3
+ require 'generators/active_record/aasm_generator'
4
+
5
+ describe ActiveRecord::Generators::AASMGenerator, type: :generator do
6
+ destination File.expand_path("../../../tmp", __FILE__)
7
+
8
+ before(:all) do
9
+ prepare_destination
10
+ end
11
+
12
+ it "creates model with aasm block for default column_name" do
13
+ run_generator %w(user)
14
+ assert_file "app/models/user.rb", /include AASM\n\n aasm do\n end\n/
15
+ end
16
+
17
+ it "creates model with aasm block for custom column_name" do
18
+ run_generator %w(user state)
19
+ assert_file "app/models/user.rb", /aasm :column => 'state' do\n end\n/
20
+ end
21
+
22
+ it "creates model with aasm block for namespaced model" do
23
+ run_generator %w(Admin::User state)
24
+ assert_file "app/models/admin/user.rb", /aasm :column => 'state' do\n end\n/
25
+ end
26
+
27
+ it "creates migration for model with aasm_column" do
28
+ run_generator %w(post)
29
+ assert_migration "db/migrate/aasm_create_posts.rb", /create_table(:posts) do |t|\n t.string :aasm_state\n/
30
+ end
31
+
32
+ it "add aasm_column in existing model" do
33
+ run_generator %w(job)
34
+ assert_file "app/models/job.rb"
35
+ run_generator %w(job)
36
+ assert_migration "db/migrate/add_aasm_state_to_jobs.rb"
37
+ end
38
+
39
+ end
@@ -0,0 +1,33 @@
1
+ require 'spec_helper'
2
+ require 'generator_spec'
3
+ require 'generators/mongoid/aasm_generator'
4
+
5
+ begin
6
+ require "mongoid"
7
+
8
+ describe Mongoid::Generators::AASMGenerator, type: :generator do
9
+ destination File.expand_path("../../../tmp", __FILE__)
10
+
11
+ before(:all) do
12
+ prepare_destination
13
+ end
14
+
15
+ it "creates model with aasm block for default column_name" do
16
+ run_generator %w(user)
17
+ assert_file "app/models/user.rb", /include AASM\n\n aasm do\n end\n/
18
+ end
19
+
20
+ it "creates model with aasm block for custom column_name" do
21
+ run_generator %w(user state)
22
+ assert_file "app/models/user.rb", /aasm :column => 'state' do\n end\n/
23
+ end
24
+
25
+ it "creates model with aasm block for namespaced model" do
26
+ run_generator %w(Admin::User state)
27
+ assert_file "app/models/admin/user.rb", /aasm :column => 'state' do\n end\n/
28
+ end
29
+
30
+ end
31
+ rescue LoadError
32
+ puts "Not running Mongoid specs because mongoid gem is not installed!!!"
33
+ end
@@ -0,0 +1,38 @@
1
+ class WithEnumWithoutColumn < ActiveRecord::Base
2
+ include AASM
3
+
4
+ if ActiveRecord::VERSION::MAJOR >= 4 && ActiveRecord::VERSION::MINOR >= 1 # won't work with Rails <= 4.1
5
+ enum status: {
6
+ opened: 0,
7
+ closed: 1
8
+ }
9
+ end
10
+
11
+ aasm :column => :status do
12
+ state :closed, initial: true
13
+ state :opened
14
+
15
+ event :view do
16
+ transitions :to => :opened, :from => :closed
17
+ end
18
+ end
19
+ end
20
+
21
+ class MultipleWithEnumWithoutColumn < ActiveRecord::Base
22
+ include AASM
23
+ if ActiveRecord::VERSION::MAJOR >= 4 && ActiveRecord::VERSION::MINOR >= 1 # won't work with Rails <= 4.1
24
+ enum status: {
25
+ opened: 0,
26
+ closed: 1
27
+ }
28
+ end
29
+
30
+ aasm :left, :column => :status do
31
+ state :closed, initial: true
32
+ state :opened
33
+
34
+ event :view do
35
+ transitions :to => :opened, :from => :closed
36
+ end
37
+ end
38
+ end
@@ -1,6 +1,9 @@
1
1
  class Guardian
2
2
  include AASM
3
3
 
4
+ def inner_guard(options={})
5
+ end
6
+
4
7
  aasm do
5
8
  state :alpha, :initial => true
6
9
  state :beta
@@ -12,6 +15,13 @@ class Guardian
12
15
  transitions :from => :alpha, :to => :beta, :guard => :fail
13
16
  end
14
17
 
18
+ event :use_proc_guard_with_params do
19
+ transitions :from => :alpha, :to => :beta, :guard => Proc.new { |options={}| inner_guard(options) }
20
+ end
21
+ event :use_lambda_guard_with_params do
22
+ transitions :from => :alpha, :to => :beta, :guard => lambda { |options={}| inner_guard(options) }
23
+ end
24
+
15
25
  event :use_guards_that_succeed do
16
26
  transitions :from => :alpha, :to => :beta, :guards => [:succeed, :another_succeed]
17
27
  end
@@ -1,6 +1,11 @@
1
1
  class Silencer
2
2
  include AASM
3
3
 
4
+ # yes, this line is here on purpose
5
+ # by this, we test if overriding configuration options works if
6
+ # the state machine is "re-opened"
7
+ aasm :whiny_transitions => true
8
+
4
9
  aasm :whiny_transitions => false do
5
10
  state :silent, :initial => true
6
11
  state :crying
@@ -27,6 +27,18 @@ describe "per-transition guards" do
27
27
  expect { guardian.use_guards_where_the_second_fails! }.to raise_error(AASM::InvalidTransition)
28
28
  expect(guardian).to be_alpha
29
29
  end
30
+
31
+ describe "with params" do
32
+ it "using a Proc" do
33
+ expect(guardian).to receive(:inner_guard).with({:flag => true}).and_return(true)
34
+ guardian.use_proc_guard_with_params(:flag => true)
35
+ end
36
+
37
+ it "using a lambda" do
38
+ expect(guardian).to receive(:inner_guard).with({:flag => true}).and_return(true)
39
+ guardian.use_lambda_guard_with_params(:flag => true)
40
+ end
41
+ end
30
42
  end
31
43
 
32
44
  describe "event guards" do
@@ -113,6 +113,20 @@ describe "instance methods" do
113
113
  end
114
114
  end
115
115
  end
116
+
117
+ if ActiveRecord::VERSION::MAJOR >= 4 && ActiveRecord::VERSION::MINOR >= 1 # won't work with Rails <= 4.1
118
+ # Enum are introduced from Rails 4.1, therefore enum syntax will not work on Rails <= 4.1
119
+ context "when AASM enum setting is not enabled and aasm column not present" do
120
+
121
+ let(:multiple_with_enum_without_column) {MultipleWithEnumWithoutColumn.new}
122
+
123
+ it "should raise NoMethodError for transitions" do
124
+ expect{multiple_with_enum_without_column.send(:view, :left)}.to raise_error(NoMethodError, "undefined method 'status' for MultipleWithEnumWithoutColumn")
125
+ end
126
+ end
127
+
128
+ end
129
+
116
130
  end
117
131
 
118
132
  context "when AASM is configured to use enum" do
@@ -298,6 +312,19 @@ describe "named scopes with the new DSL" do
298
312
  it "does not create scopes if requested" do
299
313
  expect(MultipleNoScope).not_to respond_to(:pending)
300
314
  end
315
+
316
+ context "result of scope" do
317
+ let!(:dsl1) { MultipleSimpleNewDsl.create!(status: :new) }
318
+ let!(:dsl2) { MultipleSimpleNewDsl.create!(status: :unknown_scope) }
319
+
320
+ after do
321
+ MultipleSimpleNewDsl.destroy_all
322
+ end
323
+
324
+ it "created scope works as where(name: :scope_name)" do
325
+ expect(MultipleSimpleNewDsl.unknown_scope).to contain_exactly(dsl2)
326
+ end
327
+ end
301
328
  end # scopes
302
329
 
303
330
  describe "direct assignment" do
@@ -113,6 +113,20 @@ describe "instance methods" do
113
113
  end
114
114
  end
115
115
  end
116
+
117
+ if ActiveRecord::VERSION::MAJOR >= 4 && ActiveRecord::VERSION::MINOR >= 1 # won't work with Rails <= 4.1
118
+ # Enum are introduced from Rails 4.1, therefore enum syntax will not work on Rails <= 4.1
119
+ context "when AASM enum setting is not enabled and aasm column not present" do
120
+
121
+ let(:with_enum_without_column) {WithEnumWithoutColumn.new}
122
+
123
+ it "should raise NoMethodError for transitions" do
124
+ expect{with_enum_without_column.send(:view)}.to raise_error(NoMethodError, "undefined method 'status' for WithEnumWithoutColumn")
125
+ end
126
+ end
127
+
128
+ end
129
+
116
130
  end
117
131
 
118
132
  context "when AASM is configured to use enum" do
@@ -299,6 +313,18 @@ describe "named scopes with the new DSL" do
299
313
  expect(NoScope).not_to respond_to(:pending)
300
314
  end
301
315
 
316
+ context "result of scope" do
317
+ let!(:dsl1) { SimpleNewDsl.create!(status: :new) }
318
+ let!(:dsl2) { SimpleNewDsl.create!(status: :unknown_scope) }
319
+
320
+ after do
321
+ SimpleNewDsl.destroy_all
322
+ end
323
+
324
+ it "created scope works as where(name: :scope_name)" do
325
+ expect(SimpleNewDsl.unknown_scope).to contain_exactly(dsl2)
326
+ end
327
+ end
302
328
  end # scopes
303
329
 
304
330
  describe "direct assignment" do
@@ -31,7 +31,7 @@ describe 'transitions' do
31
31
  expect(silencer).to be_smiling
32
32
  end
33
33
 
34
- it 'should call the block when success' do
34
+ it 'should call the block on success' do
35
35
  silencer = Silencer.new
36
36
  success = false
37
37
  expect {
@@ -41,7 +41,7 @@ describe 'transitions' do
41
41
  }.to change { success }.to(true)
42
42
  end
43
43
 
44
- it 'should not call the block when failure' do
44
+ it 'should not call the block on failure' do
45
45
  silencer = Silencer.new
46
46
  success = false
47
47
  expect {
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: aasm
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.5.0
4
+ version: 4.6.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Scott Barron
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2015-11-16 00:00:00.000000000 Z
13
+ date: 2016-01-08 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: rake
@@ -54,6 +54,20 @@ dependencies:
54
54
  - - ">="
55
55
  - !ruby/object:Gem::Version
56
56
  version: '3'
57
+ - !ruby/object:Gem::Dependency
58
+ name: generator_spec
59
+ requirement: !ruby/object:Gem::Requirement
60
+ requirements:
61
+ - - ">="
62
+ - !ruby/object:Gem::Version
63
+ version: '0'
64
+ type: :development
65
+ prerelease: false
66
+ version_requirements: !ruby/object:Gem::Requirement
67
+ requirements:
68
+ - - ">="
69
+ - !ruby/object:Gem::Version
70
+ version: '0'
57
71
  - !ruby/object:Gem::Dependency
58
72
  name: pry
59
73
  requirement: !ruby/object:Gem::Requirement
@@ -90,7 +104,7 @@ files:
90
104
  - Rakefile
91
105
  - aasm.gemspec
92
106
  - callbacks.txt
93
- - gemfiles/rails_3.2.gemfile
107
+ - gemfiles/rails_3.2_stable.gemfile
94
108
  - gemfiles/rails_4.0.gemfile
95
109
  - gemfiles/rails_4.0_mongo_mapper.gemfile
96
110
  - gemfiles/rails_4.1.gemfile
@@ -123,10 +137,18 @@ files:
123
137
  - lib/aasm/rspec/transition_from.rb
124
138
  - lib/aasm/state_machine.rb
125
139
  - lib/aasm/version.rb
140
+ - lib/generators/aasm/aasm_generator.rb
141
+ - lib/generators/aasm/orm_helpers.rb
142
+ - lib/generators/active_record/aasm_generator.rb
143
+ - lib/generators/active_record/templates/migration.rb
144
+ - lib/generators/active_record/templates/migration_existing.rb
145
+ - lib/generators/mongoid/aasm_generator.rb
126
146
  - spec/database.rb
127
147
  - spec/database.yml
128
148
  - spec/en.yml
129
149
  - spec/en_deprecated_style.yml
150
+ - spec/generators/active_record_generator_spec.rb
151
+ - spec/generators/mongoid_generator_spec.rb
130
152
  - spec/models/active_record/basic_active_record_two_state_machines_example.rb
131
153
  - spec/models/active_record/complex_active_record_example.rb
132
154
  - spec/models/active_record/derivate_new_dsl.rb
@@ -143,6 +165,7 @@ files:
143
165
  - spec/models/active_record/thief.rb
144
166
  - spec/models/active_record/transient.rb
145
167
  - spec/models/active_record/with_enum.rb
168
+ - spec/models/active_record/with_enum_without_column.rb
146
169
  - spec/models/active_record/with_false_enum.rb
147
170
  - spec/models/active_record/with_true_enum.rb
148
171
  - spec/models/active_record/writer.rb
@@ -256,7 +279,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
256
279
  version: '0'
257
280
  requirements: []
258
281
  rubyforge_project:
259
- rubygems_version: 2.2.2
282
+ rubygems_version: 2.4.5
260
283
  signing_key:
261
284
  specification_version: 4
262
285
  summary: State machine mixin for Ruby objects
@@ -265,6 +288,8 @@ test_files:
265
288
  - spec/database.yml
266
289
  - spec/en.yml
267
290
  - spec/en_deprecated_style.yml
291
+ - spec/generators/active_record_generator_spec.rb
292
+ - spec/generators/mongoid_generator_spec.rb
268
293
  - spec/models/active_record/basic_active_record_two_state_machines_example.rb
269
294
  - spec/models/active_record/complex_active_record_example.rb
270
295
  - spec/models/active_record/derivate_new_dsl.rb
@@ -281,6 +306,7 @@ test_files:
281
306
  - spec/models/active_record/thief.rb
282
307
  - spec/models/active_record/transient.rb
283
308
  - spec/models/active_record/with_enum.rb
309
+ - spec/models/active_record/with_enum_without_column.rb
284
310
  - spec/models/active_record/with_false_enum.rb
285
311
  - spec/models/active_record/with_true_enum.rb
286
312
  - spec/models/active_record/writer.rb