aasm 4.0.8 → 4.5.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (147) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +7 -2
  3. data/CHANGELOG.md +43 -2
  4. data/CODE_OF_CONDUCT.md +13 -0
  5. data/Gemfile +6 -3
  6. data/LICENSE +1 -1
  7. data/PLANNED_CHANGES.md +8 -4
  8. data/README.md +171 -14
  9. data/aasm.gemspec +1 -5
  10. data/gemfiles/rails_3.2.gemfile +3 -2
  11. data/gemfiles/rails_4.0.gemfile +2 -6
  12. data/gemfiles/rails_4.0_mongo_mapper.gemfile +14 -0
  13. data/gemfiles/rails_4.1.gemfile +2 -6
  14. data/gemfiles/rails_4.1_mongo_mapper.gemfile +14 -0
  15. data/gemfiles/rails_4.2.gemfile +1 -5
  16. data/gemfiles/rails_4.2_mongo_mapper.gemfile +14 -0
  17. data/gemfiles/rails_4.2_mongoid_5.gemfile +12 -0
  18. data/lib/aasm/aasm.rb +69 -36
  19. data/lib/aasm/base.rb +51 -21
  20. data/lib/aasm/core/event.rb +7 -6
  21. data/lib/aasm/core/state.rb +11 -8
  22. data/lib/aasm/core/transition.rb +7 -5
  23. data/lib/aasm/errors.rb +15 -1
  24. data/lib/aasm/instance_base.rb +17 -13
  25. data/lib/aasm/localizer.rb +1 -1
  26. data/lib/aasm/persistence/active_record_persistence.rb +63 -73
  27. data/lib/aasm/persistence/base.rb +55 -20
  28. data/lib/aasm/persistence/mongo_mapper_persistence.rb +157 -0
  29. data/lib/aasm/persistence/mongoid_persistence.rb +16 -41
  30. data/lib/aasm/persistence/plain_persistence.rb +8 -7
  31. data/lib/aasm/persistence/sequel_persistence.rb +12 -9
  32. data/lib/aasm/persistence.rb +2 -0
  33. data/lib/aasm/rspec/allow_event.rb +22 -0
  34. data/lib/aasm/rspec/allow_transition_to.rb +22 -0
  35. data/lib/aasm/rspec/have_state.rb +22 -0
  36. data/lib/aasm/rspec/transition_from.rb +32 -0
  37. data/lib/aasm/rspec.rb +5 -0
  38. data/lib/aasm/state_machine.rb +20 -6
  39. data/lib/aasm/version.rb +1 -1
  40. data/spec/database.rb +27 -1
  41. data/spec/models/active_record/basic_active_record_two_state_machines_example.rb +25 -0
  42. data/spec/models/active_record/complex_active_record_example.rb +33 -0
  43. data/spec/models/active_record/derivate_new_dsl.rb +7 -0
  44. data/spec/models/active_record/false_state.rb +35 -0
  45. data/spec/models/active_record/gate.rb +39 -0
  46. data/spec/models/active_record/localizer_test_model.rb +34 -0
  47. data/spec/models/active_record/no_direct_assignment.rb +21 -0
  48. data/spec/models/active_record/no_scope.rb +21 -0
  49. data/spec/models/active_record/persisted_state.rb +12 -0
  50. data/spec/models/active_record/provided_and_persisted_state.rb +24 -0
  51. data/spec/models/active_record/reader.rb +7 -0
  52. data/spec/models/active_record/readme_job.rb +21 -0
  53. data/spec/models/active_record/simple_new_dsl.rb +17 -0
  54. data/spec/models/active_record/thief.rb +29 -0
  55. data/spec/models/active_record/transient.rb +6 -0
  56. data/spec/models/active_record/with_enum.rb +39 -0
  57. data/spec/models/active_record/with_false_enum.rb +31 -0
  58. data/spec/models/active_record/with_true_enum.rb +39 -0
  59. data/spec/models/active_record/writer.rb +6 -0
  60. data/spec/models/basic_two_state_machines_example.rb +25 -0
  61. data/spec/models/callbacks/basic.rb +3 -0
  62. data/spec/models/callbacks/basic_multiple.rb +75 -0
  63. data/spec/models/callbacks/guard_within_block_multiple.rb +66 -0
  64. data/spec/models/callbacks/multiple_transitions_transition_guard_multiple.rb +65 -0
  65. data/spec/models/callbacks/private_method_multiple.rb +44 -0
  66. data/spec/models/callbacks/with_args.rb +9 -9
  67. data/spec/models/callbacks/with_args_multiple.rb +61 -0
  68. data/spec/models/callbacks/{with_state_args.rb → with_state_arg.rb} +1 -1
  69. data/spec/models/callbacks/with_state_arg_multiple.rb +26 -0
  70. data/spec/models/complex_example.rb +222 -0
  71. data/spec/models/conversation.rb +47 -1
  72. data/spec/models/default_state.rb +12 -0
  73. data/spec/models/foo.rb +57 -0
  74. data/spec/models/foo_callback_multiple.rb +45 -0
  75. data/spec/models/guardian.rb +10 -0
  76. data/spec/models/guardian_multiple.rb +48 -0
  77. data/spec/models/initial_state_proc.rb +31 -0
  78. data/spec/models/invalid_persistor.rb +15 -0
  79. data/spec/models/mongo_mapper/complex_mongo_mapper_example.rb +37 -0
  80. data/spec/models/mongo_mapper/no_scope_mongo_mapper.rb +21 -0
  81. data/spec/models/mongo_mapper/simple_mongo_mapper.rb +23 -0
  82. data/spec/models/mongo_mapper/simple_new_dsl_mongo_mapper.rb +25 -0
  83. data/spec/models/mongoid/complex_mongoid_example.rb +37 -0
  84. data/spec/models/mongoid/no_scope_mongoid.rb +11 -0
  85. data/spec/models/mongoid/simple_mongoid.rb +12 -0
  86. data/spec/models/mongoid/simple_new_dsl_mongoid.rb +14 -1
  87. data/spec/models/no_initial_state.rb +25 -0
  88. data/spec/models/parametrised_event.rb +1 -1
  89. data/spec/models/parametrised_event_multiple.rb +29 -0
  90. data/spec/models/provided_state.rb +24 -0
  91. data/spec/models/sequel/complex_sequel_example.rb +45 -0
  92. data/spec/models/sequel/sequel_multiple.rb +25 -0
  93. data/spec/models/sequel/sequel_simple.rb +25 -0
  94. data/spec/models/silencer.rb +5 -0
  95. data/spec/models/simple_example.rb +15 -0
  96. data/spec/models/simple_multiple_example.rb +30 -0
  97. data/spec/models/state_machine_with_failed_event.rb +12 -0
  98. data/spec/models/sub_class.rb +7 -0
  99. data/spec/models/sub_class_with_more_states.rb +18 -0
  100. data/spec/models/super_class.rb +46 -0
  101. data/spec/models/transactor.rb +27 -0
  102. data/spec/models/valid_state_name.rb +23 -0
  103. data/spec/models/validator.rb +47 -0
  104. data/spec/spec_helper.rb +4 -4
  105. data/spec/unit/api_spec.rb +6 -1
  106. data/spec/unit/basic_two_state_machines_example_spec.rb +10 -0
  107. data/spec/unit/callback_multiple_spec.rb +295 -0
  108. data/spec/unit/callbacks_spec.rb +3 -2
  109. data/spec/unit/complex_example_spec.rb +2 -2
  110. data/spec/unit/complex_multiple_example_spec.rb +99 -0
  111. data/spec/unit/edge_cases_spec.rb +16 -0
  112. data/spec/unit/event_multiple_spec.rb +73 -0
  113. data/spec/unit/event_naming_spec.rb +2 -15
  114. data/spec/unit/event_spec.rb +11 -6
  115. data/spec/unit/guard_multiple_spec.rb +60 -0
  116. data/spec/unit/guard_spec.rb +12 -0
  117. data/spec/unit/initial_state_multiple_spec.rb +15 -0
  118. data/spec/unit/initial_state_spec.rb +3 -18
  119. data/spec/unit/inspection_multiple_spec.rb +201 -0
  120. data/spec/unit/inspection_spec.rb +12 -7
  121. data/spec/unit/localizer_spec.rb +0 -38
  122. data/spec/unit/persistence/active_record_persistence_multiple_spec.rb +573 -0
  123. data/spec/unit/persistence/active_record_persistence_spec.rb +70 -13
  124. data/spec/unit/persistence/mongo_mapper_persistence_multiple_spec.rb +146 -0
  125. data/spec/unit/persistence/mongo_mapper_persistence_spec.rb +93 -0
  126. data/spec/unit/persistence/mongoid_persistence_multiple_spec.rb +127 -0
  127. data/spec/unit/persistence/mongoid_persistence_spec.rb +79 -0
  128. data/spec/unit/persistence/sequel_persistence_multiple_spec.rb +153 -0
  129. data/spec/unit/persistence/sequel_persistence_spec.rb +20 -23
  130. data/spec/unit/readme_spec.rb +42 -0
  131. data/spec/unit/reloading_spec.rb +1 -1
  132. data/spec/unit/rspec_matcher_spec.rb +79 -0
  133. data/spec/unit/simple_example_spec.rb +26 -42
  134. data/spec/unit/simple_multiple_example_spec.rb +63 -0
  135. data/spec/unit/state_spec.rb +3 -1
  136. data/spec/unit/subclassing_multiple_spec.rb +39 -0
  137. data/spec/unit/subclassing_spec.rb +10 -10
  138. data/spec/unit/transition_spec.rb +39 -25
  139. metadata +152 -23
  140. data/spec/models/active_record/api.rb +0 -75
  141. data/spec/models/argument.rb +0 -11
  142. data/spec/models/auth_machine.rb +0 -88
  143. data/spec/models/bar.rb +0 -15
  144. data/spec/models/father.rb +0 -21
  145. data/spec/models/persistence.rb +0 -164
  146. data/spec/models/son.rb +0 -3
  147. data/spec/unit/persistence/mongoid_persistance_spec.rb +0 -152
@@ -1,88 +0,0 @@
1
- class AuthMachine
2
- include AASM
3
-
4
- attr_accessor :activation_code, :activated_at, :deleted_at
5
-
6
- aasm do
7
- state :passive
8
- state :pending, :initial => true, :before_enter => :make_activation_code
9
- state :active, :before_enter => :do_activate
10
- state :suspended
11
- state :deleted, :before_enter => :do_delete#, :exit => :do_undelete
12
- state :waiting
13
-
14
- event :register do
15
- transitions :from => :passive, :to => :pending do
16
- guard do
17
- can_register?
18
- end
19
- end
20
- end
21
-
22
- event :activate do
23
- transitions :from => :pending, :to => :active
24
- end
25
-
26
- event :suspend do
27
- transitions :from => [:passive, :pending, :active], :to => :suspended
28
- end
29
-
30
- event :delete do
31
- transitions :from => [:passive, :pending, :active, :suspended], :to => :deleted
32
- end
33
-
34
- # a dummy event that can never happen
35
- event :unpassify do
36
- transitions :from => :passive, :to => :active, :guard => Proc.new {|u| false }
37
- end
38
-
39
- event :unsuspend do
40
- transitions :from => :suspended, :to => :active, :guard => Proc.new { has_activated? }
41
- transitions :from => :suspended, :to => :pending, :guard => :has_activation_code?
42
- transitions :from => :suspended, :to => :passive
43
- end
44
-
45
- event :wait do
46
- transitions :from => :suspended, :to => :waiting, :guard => :if_polite?
47
- end
48
- end
49
-
50
- def initialize
51
- # the AR backend uses a before_validate_on_create :aasm_ensure_initial_state
52
- # lets do something similar here for testing purposes.
53
- aasm.enter_initial_state
54
- end
55
-
56
- def make_activation_code
57
- @activation_code = 'moo'
58
- end
59
-
60
- def do_activate
61
- @activated_at = Time.now
62
- @activation_code = nil
63
- end
64
-
65
- def do_delete
66
- @deleted_at = Time.now
67
- end
68
-
69
- def do_undelete
70
- @deleted_at = false
71
- end
72
-
73
- def can_register?
74
- true
75
- end
76
-
77
- def has_activated?
78
- !!@activated_at
79
- end
80
-
81
- def has_activation_code?
82
- !!@activation_code
83
- end
84
-
85
- def if_polite?(phrase = nil)
86
- phrase == :please
87
- end
88
- end
data/spec/models/bar.rb DELETED
@@ -1,15 +0,0 @@
1
- class Bar
2
- include AASM
3
-
4
- aasm do
5
- state :read
6
- state :ended
7
-
8
- event :foo do
9
- transitions :to => :ended, :from => [:read]
10
- end
11
- end
12
- end
13
-
14
- class Baz < Bar
15
- end
@@ -1,21 +0,0 @@
1
- require 'active_record'
2
-
3
- class Father < ActiveRecord::Base
4
- include AASM
5
-
6
- aasm do
7
- state :missing_details, :initial => true
8
- state :pending_details_confirmation
9
-
10
- event :add_details do
11
- transitions :from => :missing_details, :to => :pending_details_confirmation
12
- end
13
- end
14
-
15
- def update_state
16
- if may_add_details?
17
- add_details!
18
- end
19
- end
20
-
21
- end
@@ -1,164 +0,0 @@
1
- class Gate < ActiveRecord::Base
2
- include AASM
3
-
4
- # Fake this column for testing purposes
5
- # attr_accessor :aasm_state
6
-
7
- def value
8
- 'value'
9
- end
10
-
11
- aasm do
12
- state :opened
13
- state :closed
14
-
15
- event :view do
16
- transitions :to => :read, :from => [:needs_attention]
17
- end
18
- end
19
- end
20
-
21
- class FalseState < ActiveRecord::Base
22
- include AASM
23
-
24
- def initialize(*args)
25
- super
26
- self.aasm_state = false
27
- end
28
-
29
- aasm do
30
- state :opened
31
- state :closed
32
-
33
- event :view do
34
- transitions :to => :read, :from => [:needs_attention]
35
- end
36
- end
37
- end
38
-
39
- class WithEnum < ActiveRecord::Base
40
- include AASM
41
-
42
- # Fake this column for testing purposes
43
- attr_accessor :aasm_state
44
-
45
- def self.test
46
- {}
47
- end
48
-
49
- aasm :enum => :test do
50
- state :opened
51
- state :closed
52
-
53
- event :view do
54
- transitions :to => :read, :from => [:needs_attention]
55
- end
56
- end
57
- end
58
-
59
- class WithTrueEnum < ActiveRecord::Base
60
- include AASM
61
-
62
- # Fake this column for testing purposes
63
- attr_accessor :aasm_state
64
-
65
- def value
66
- 'value'
67
- end
68
-
69
- aasm :enum => true do
70
- state :opened
71
- state :closed
72
-
73
- event :view do
74
- transitions :to => :read, :from => [:needs_attention]
75
- end
76
- end
77
- end
78
-
79
- class WithFalseEnum < ActiveRecord::Base
80
- include AASM
81
-
82
- # Fake this column for testing purposes
83
- attr_accessor :aasm_state
84
-
85
- aasm :enum => false do
86
- state :opened
87
- state :closed
88
-
89
- event :view do
90
- transitions :to => :read, :from => [:needs_attention]
91
- end
92
- end
93
- end
94
-
95
- class Reader < ActiveRecord::Base
96
- include AASM
97
-
98
- def aasm_read_state
99
- "fi"
100
- end
101
- end
102
-
103
- class Writer < ActiveRecord::Base
104
- def aasm_write_state(state)
105
- "fo"
106
- end
107
- include AASM
108
- end
109
-
110
- class Transient < ActiveRecord::Base
111
- def aasm_write_state_without_persistence(state)
112
- "fum"
113
- end
114
- include AASM
115
- end
116
-
117
- class SimpleNewDsl < ActiveRecord::Base
118
- include AASM
119
- aasm :column => :status
120
- aasm do
121
- state :unknown_scope
122
- state :new
123
- end
124
- end
125
-
126
- class NoScope < ActiveRecord::Base
127
- include AASM
128
- aasm :create_scopes => false do
129
- state :pending, :initial => true
130
- state :running
131
- event :run do
132
- transitions :from => :pending, :to => :running
133
- end
134
- end
135
- end
136
-
137
- class NoDirectAssignment < ActiveRecord::Base
138
- include AASM
139
- aasm :no_direct_assignment => true do
140
- state :pending, :initial => true
141
- state :running
142
- event :run do
143
- transitions :from => :pending, :to => :running
144
- end
145
- end
146
- end
147
-
148
- class DerivateNewDsl < SimpleNewDsl
149
- end
150
-
151
- class Thief < ActiveRecord::Base
152
- if ActiveRecord::VERSION::MAJOR >= 3
153
- self.table_name = 'thieves'
154
- else
155
- set_table_name "thieves"
156
- end
157
- include AASM
158
- aasm do
159
- state :rich
160
- state :jailed
161
- initial_state Proc.new {|thief| thief.skilled ? :rich : :jailed }
162
- end
163
- attr_accessor :skilled, :aasm_state
164
- end
data/spec/models/son.rb DELETED
@@ -1,3 +0,0 @@
1
- class Son < Father
2
- include AASM
3
- end
@@ -1,152 +0,0 @@
1
- describe 'mongoid', :if => Gem::Version.create(RUBY_VERSION.dup) >= Gem::Version.create('1.9.3') do
2
- # describe 'mongoid' do
3
-
4
- begin
5
- require 'mongoid'
6
- require 'logger'
7
- require 'spec_helper'
8
-
9
- before(:all) do
10
- Dir[File.dirname(__FILE__) + "/../../models/mongoid/*.rb"].sort.each { |f| require File.expand_path(f) }
11
-
12
- # if you want to see the statements while running the spec enable the following line
13
- # Mongoid.logger = Logger.new(STDERR)
14
-
15
- DATABASE_NAME = "mongoid_#{Process.pid}"
16
-
17
- Mongoid.configure do |config|
18
- config.connect_to DATABASE_NAME
19
- end
20
- end
21
-
22
- after do
23
- Mongoid.purge!
24
- end
25
-
26
- describe "named scopes with the old DSL" do
27
-
28
- context "Does not already respond_to? the scope name" do
29
- it "should add a scope" do
30
- expect(SimpleMongoid).to respond_to(:unknown_scope)
31
- expect(SimpleMongoid.unknown_scope.class).to eq(Mongoid::Criteria)
32
- end
33
- end
34
-
35
- context "Already respond_to? the scope name" do
36
- it "should not add a scope" do
37
- expect(SimpleMongoid).to respond_to(:new)
38
- expect(SimpleMongoid.new.class).to eq(SimpleMongoid)
39
- end
40
- end
41
-
42
- end
43
-
44
- describe "named scopes with the new DSL" do
45
-
46
- context "Does not already respond_to? the scope name" do
47
- it "should add a scope" do
48
- expect(SimpleNewDslMongoid).to respond_to(:unknown_scope)
49
- expect(SimpleNewDslMongoid.unknown_scope.class).to eq(Mongoid::Criteria)
50
- end
51
- end
52
-
53
- context "Already respond_to? the scope name" do
54
- it "should not add a scope" do
55
- expect(SimpleNewDslMongoid).to respond_to(:new)
56
- expect(SimpleNewDslMongoid.new.class).to eq(SimpleNewDslMongoid)
57
- end
58
- end
59
-
60
- it "does not create scopes if requested" do
61
- expect(NoScopeMongoid).not_to respond_to(:ignored_scope)
62
- end
63
-
64
- end
65
-
66
- describe "#find_in_state" do
67
-
68
- let!(:model) { SimpleNewDslMongoid.create!(:status => :unknown_scope) }
69
- let!(:model_id) { model._id }
70
-
71
- it "should respond to method" do
72
- expect(SimpleNewDslMongoid).to respond_to(:find_in_state)
73
- end
74
-
75
- it "should find the model when given the correct scope and model id" do
76
- expect(SimpleNewDslMongoid.find_in_state(model_id, 'unknown_scope').class).to eq(SimpleNewDslMongoid)
77
- expect(SimpleNewDslMongoid.find_in_state(model_id, 'unknown_scope')).to eq(model)
78
- end
79
-
80
- it "should raise DocumentNotFound error when given incorrect scope" do
81
- expect {SimpleNewDslMongoid.find_in_state(model_id, 'new')}.to raise_error Mongoid::Errors::DocumentNotFound
82
- end
83
-
84
- it "should raise DocumentNotFound error when given incorrect model id" do
85
- expect {SimpleNewDslMongoid.find_in_state('bad_id', 'unknown_scope')}.to raise_error Mongoid::Errors::DocumentNotFound
86
- end
87
-
88
- end
89
-
90
- describe "#count_in_state" do
91
-
92
- before do
93
- 3.times { SimpleNewDslMongoid.create!(:status => :unknown_scope) }
94
- end
95
-
96
- it "should respond to method" do
97
- expect(SimpleNewDslMongoid).to respond_to(:count_in_state)
98
- end
99
-
100
- it "should return n for a scope with n records persisted" do
101
- expect(SimpleNewDslMongoid.count_in_state('unknown_scope').class).to eq(Fixnum)
102
- expect(SimpleNewDslMongoid.count_in_state('unknown_scope')).to eq(3)
103
- end
104
-
105
- it "should return zero for a scope without records persisted" do
106
- expect(SimpleNewDslMongoid.count_in_state('new').class).to eq(Fixnum)
107
- expect(SimpleNewDslMongoid.count_in_state('new')).to eq(0)
108
- end
109
-
110
- end
111
-
112
- describe "#with_state_scope" do
113
-
114
- before do
115
- 3.times { SimpleNewDslMongoid.create!(:status => :unknown_scope) }
116
- 2.times { SimpleNewDslMongoid.create!(:status => :new) }
117
- end
118
-
119
- it "should respond to method" do
120
- expect(SimpleNewDslMongoid).to respond_to(:with_state_scope)
121
- end
122
-
123
- it "should correctly process block" do
124
- expect(SimpleNewDslMongoid.with_state_scope('unknown_scope') do
125
- SimpleNewDslMongoid.count
126
- end).to eq(3)
127
- expect(SimpleNewDslMongoid.with_state_scope('new') do
128
- SimpleNewDslMongoid.count
129
- end).to eq(2)
130
- end
131
-
132
- end
133
-
134
-
135
- describe "instance methods" do
136
- let(:simple) {SimpleNewDslMongoid.new}
137
-
138
- it "should call aasm_ensure_initial_state on validation before create" do
139
- expect(simple).to receive(:aasm_ensure_initial_state).and_return(true)
140
- simple.valid?
141
- end
142
-
143
- it "should call aasm_ensure_initial_state before create, even if skipping validations" do
144
- expect(simple).to receive(:aasm_ensure_initial_state).and_return(true)
145
- simple.save(:validate => false)
146
- end
147
- end
148
-
149
- rescue LoadError
150
- puts "Not running Mongoid specs because mongoid gem is not installed!!!"
151
- end
152
- end