state_machines-activerecord 0.3.0 → 0.4.0.pre
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 +4 -4
- data/.travis.yml +6 -0
- data/Appraisals +10 -0
- data/README.md +6 -7
- data/gemfiles/active_record_edge.gemfile +17 -0
- data/lib/state_machines/integrations/active_record.rb +108 -99
- data/lib/state_machines/integrations/active_record/version.rb +1 -1
- data/state_machines-activerecord.gemspec +2 -2
- metadata +16 -8
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b08f23fe776a36406ccb74f5d177acb8a6fc030e
|
4
|
+
data.tar.gz: fa00fc7d5506ca635f50682c159393e39a15b88c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9ae6270e99bac4395564478cb42fd2d6b9a787055e670d47f4f760d2f8c6a2e5747d9283d6f82a55717c853658e0c0b6a855931acfa82f5b3a06ae1ec931e6b2
|
7
|
+
data.tar.gz: b4fe5baa32f92b424e6df7c45216385fd971d7ba191be7dc2b6998aae1b096106ec54abb344a3c9633317068048db004016716e02b0bc6d25f1d65acaf8e9d61
|
data/.travis.yml
CHANGED
@@ -13,6 +13,12 @@ gemfile:
|
|
13
13
|
- gemfiles/active_record_4.2.gemfile
|
14
14
|
|
15
15
|
matrix:
|
16
|
+
include:
|
17
|
+
- gemfile: gemfiles/active_record_edge.gemfile
|
18
|
+
rvm: 2.2
|
16
19
|
allow_failures:
|
17
20
|
- rvm: jruby
|
18
21
|
- rvm: rbx-2
|
22
|
+
- gemfile: gemfiles/active_record_edge.gemfile
|
23
|
+
rvm: 2.2
|
24
|
+
|
data/Appraisals
CHANGED
@@ -9,3 +9,13 @@ appraise "active_record_4.2" do
|
|
9
9
|
gem "activerecord-jdbcsqlite3-adapter", platform: :jruby
|
10
10
|
gem "activerecord", github: 'rails/rails', branch: '4-2-stable'
|
11
11
|
end
|
12
|
+
|
13
|
+
appraise "active_record_edge" do
|
14
|
+
gem "sqlite3", platforms: [:mri, :rbx]
|
15
|
+
gem "activerecord-jdbcsqlite3-adapter", platform: :jruby
|
16
|
+
gem "activerecord", github: 'rails/rails', branch: 'master'
|
17
|
+
gem "method_source" # appears to be a missing dependency of activerecord
|
18
|
+
gem "arel", github: 'rails/arel', branch: 'master'
|
19
|
+
gem "activemodel", github: 'rails/rails', branch: 'master'
|
20
|
+
gem "state_machines-activemodel", '0.4.0.pre'
|
21
|
+
end
|
data/README.md
CHANGED
@@ -1,11 +1,15 @@
|
|
1
1
|
[](https://travis-ci.org/state-machines/state_machines-activerecord)
|
2
|
-
[](https://codeclimate.com/github/state-machines/state_machines-activerecord)
|
3
3
|
|
4
4
|
# StateMachines Active Record Integration
|
5
5
|
|
6
|
-
The Active Record integration adds support for database transactions, automatically
|
6
|
+
The Active Record 4.1+ integration adds support for database transactions, automatically
|
7
7
|
saving the record, named scopes, validation errors.
|
8
8
|
|
9
|
+
## Dependencies
|
10
|
+
|
11
|
+
Active Record 4.1+
|
12
|
+
|
9
13
|
## Installation
|
10
14
|
|
11
15
|
Add this line to your application's Gemfile:
|
@@ -60,11 +64,6 @@ Vehicle.with_state(:parked) # also plural #with_states
|
|
60
64
|
Vehicle.without_states(:first_gear, :second_gear) # also singular #without_state
|
61
65
|
```
|
62
66
|
|
63
|
-
|
64
|
-
Dependencies
|
65
|
-
|
66
|
-
Active Record 4.1+
|
67
|
-
|
68
67
|
## Contributing
|
69
68
|
|
70
69
|
1. Fork it ( https://github.com/state-machines/state_machines-activerecord/fork )
|
@@ -0,0 +1,17 @@
|
|
1
|
+
# This file was generated by Appraisal
|
2
|
+
|
3
|
+
source "https://rubygems.org"
|
4
|
+
|
5
|
+
gem "sqlite3", :platforms => [:mri, :rbx]
|
6
|
+
gem "activerecord-jdbcsqlite3-adapter", :platform => :jruby
|
7
|
+
gem "activerecord", :github => "rails/rails", :branch => "master"
|
8
|
+
gem "method_source"
|
9
|
+
gem "arel", :github => "rails/arel", :branch => "master"
|
10
|
+
gem "activemodel", :github => "rails/rails", :branch => "master"
|
11
|
+
gem "state_machines-activemodel", "0.4.0.pre"
|
12
|
+
|
13
|
+
platforms :mri_20, :mri_21 do
|
14
|
+
gem "pry-byebug"
|
15
|
+
end
|
16
|
+
|
17
|
+
gemspec :path => "../"
|
@@ -5,12 +5,12 @@ require 'state_machines/integrations/active_record/version'
|
|
5
5
|
module StateMachines
|
6
6
|
module Integrations #:nodoc:
|
7
7
|
# Adds support for integrating state machines with ActiveRecord models.
|
8
|
-
#
|
8
|
+
#
|
9
9
|
# == Examples
|
10
|
-
#
|
10
|
+
#
|
11
11
|
# Below is an example of a simple state machine defined within an
|
12
12
|
# ActiveRecord model:
|
13
|
-
#
|
13
|
+
#
|
14
14
|
# class Vehicle < ActiveRecord::Base
|
15
15
|
# state_machine :initial => :parked do
|
16
16
|
# event :ignite do
|
@@ -18,138 +18,138 @@ module StateMachines
|
|
18
18
|
# end
|
19
19
|
# end
|
20
20
|
# end
|
21
|
-
#
|
21
|
+
#
|
22
22
|
# The examples in the sections below will use the above class as a
|
23
23
|
# reference.
|
24
|
-
#
|
24
|
+
#
|
25
25
|
# == Actions
|
26
|
-
#
|
26
|
+
#
|
27
27
|
# By default, the action that will be invoked when a state is transitioned
|
28
28
|
# is the +save+ action. This will cause the record to save the changes
|
29
29
|
# made to the state machine's attribute. *Note* that if any other changes
|
30
30
|
# were made to the record prior to transition, then those changes will
|
31
31
|
# be saved as well.
|
32
|
-
#
|
32
|
+
#
|
33
33
|
# For example,
|
34
|
-
#
|
34
|
+
#
|
35
35
|
# vehicle = Vehicle.create # => #<Vehicle id: 1, name: nil, state: "parked">
|
36
36
|
# vehicle.name = 'Ford Explorer'
|
37
37
|
# vehicle.ignite # => true
|
38
38
|
# vehicle.reload # => #<Vehicle id: 1, name: "Ford Explorer", state: "idling">
|
39
|
-
#
|
40
|
-
# *Note* that if you want a transition to update additional attributes of the record,
|
41
|
-
# either the changes need to be made in a +before_transition+ callback or you need
|
39
|
+
#
|
40
|
+
# *Note* that if you want a transition to update additional attributes of the record,
|
41
|
+
# either the changes need to be made in a +before_transition+ callback or you need
|
42
42
|
# to save the record manually.
|
43
43
|
#
|
44
44
|
# == Events
|
45
|
-
#
|
45
|
+
#
|
46
46
|
# As described in StateMachines::InstanceMethods#state_machine, event
|
47
47
|
# attributes are created for every machine that allow transitions to be
|
48
48
|
# performed automatically when the object's action (in this case, :save)
|
49
49
|
# is called.
|
50
|
-
#
|
50
|
+
#
|
51
51
|
# In ActiveRecord, these automated events are run in the following order:
|
52
52
|
# * before validation - Run before callbacks and persist new states, then validate
|
53
53
|
# * before save - If validation was skipped, run before callbacks and persist new states, then save
|
54
54
|
# * after save - Run after callbacks
|
55
|
-
#
|
55
|
+
#
|
56
56
|
# For example,
|
57
|
-
#
|
57
|
+
#
|
58
58
|
# vehicle = Vehicle.create # => #<Vehicle id: 1, name: nil, state: "parked">
|
59
59
|
# vehicle.state_event # => nil
|
60
60
|
# vehicle.state_event = 'invalid'
|
61
61
|
# vehicle.valid? # => false
|
62
62
|
# vehicle.errors.full_messages # => ["State event is invalid"]
|
63
|
-
#
|
63
|
+
#
|
64
64
|
# vehicle.state_event = 'ignite'
|
65
65
|
# vehicle.valid? # => true
|
66
66
|
# vehicle.save # => true
|
67
67
|
# vehicle.state # => "idling"
|
68
68
|
# vehicle.state_event # => nil
|
69
|
-
#
|
69
|
+
#
|
70
70
|
# Note that this can also be done on a mass-assignment basis:
|
71
|
-
#
|
71
|
+
#
|
72
72
|
# vehicle = Vehicle.create(:state_event => 'ignite') # => #<Vehicle id: 1, name: nil, state: "idling">
|
73
73
|
# vehicle.state # => "idling"
|
74
|
-
#
|
74
|
+
#
|
75
75
|
# This technique is always used for transitioning states when the +save+
|
76
76
|
# action (which is the default) is configured for the machine.
|
77
|
-
#
|
77
|
+
#
|
78
78
|
# === Security implications
|
79
|
-
#
|
79
|
+
#
|
80
80
|
# Beware that public event attributes mean that events can be fired
|
81
81
|
# whenever mass-assignment is being used. If you want to prevent malicious
|
82
82
|
# users from tampering with events through URLs / forms, the attribute
|
83
83
|
# should be protected like so:
|
84
|
-
#
|
84
|
+
#
|
85
85
|
# class Vehicle < ActiveRecord::Base
|
86
86
|
# attr_protected :state_event
|
87
87
|
# # attr_accessible ... # Alternative technique
|
88
|
-
#
|
88
|
+
#
|
89
89
|
# state_machine do
|
90
90
|
# ...
|
91
91
|
# end
|
92
92
|
# end
|
93
|
-
#
|
93
|
+
#
|
94
94
|
# If you want to only have *some* events be able to fire via mass-assignment,
|
95
95
|
# you can build two state machines (one public and one protected) like so:
|
96
|
-
#
|
96
|
+
#
|
97
97
|
# class Vehicle < ActiveRecord::Base
|
98
98
|
# attr_protected :state_event # Prevent access to events in the first machine
|
99
|
-
#
|
99
|
+
#
|
100
100
|
# state_machine do
|
101
101
|
# # Define private events here
|
102
102
|
# end
|
103
|
-
#
|
103
|
+
#
|
104
104
|
# # Public machine targets the same state as the private machine
|
105
105
|
# state_machine :public_state, :attribute => :state do
|
106
106
|
# # Define public events here
|
107
107
|
# end
|
108
108
|
# end
|
109
|
-
#
|
109
|
+
#
|
110
110
|
# == Transactions
|
111
|
-
#
|
111
|
+
#
|
112
112
|
# In order to ensure that any changes made during transition callbacks
|
113
113
|
# are rolled back during a failed attempt, every transition is wrapped
|
114
114
|
# within a transaction.
|
115
|
-
#
|
115
|
+
#
|
116
116
|
# For example,
|
117
|
-
#
|
117
|
+
#
|
118
118
|
# class Message < ActiveRecord::Base
|
119
119
|
# end
|
120
|
-
#
|
120
|
+
#
|
121
121
|
# Vehicle.state_machine do
|
122
122
|
# before_transition do |vehicle, transition|
|
123
123
|
# Message.create(:content => transition.inspect)
|
124
124
|
# false
|
125
125
|
# end
|
126
126
|
# end
|
127
|
-
#
|
127
|
+
#
|
128
128
|
# vehicle = Vehicle.create # => #<Vehicle id: 1, name: nil, state: "parked">
|
129
129
|
# vehicle.ignite # => false
|
130
130
|
# Message.count # => 0
|
131
|
-
#
|
131
|
+
#
|
132
132
|
# *Note* that only before callbacks that halt the callback chain and
|
133
133
|
# failed attempts to save the record will result in the transaction being
|
134
134
|
# rolled back. If an after callback halts the chain, the previous result
|
135
135
|
# still applies and the transaction is *not* rolled back.
|
136
|
-
#
|
136
|
+
#
|
137
137
|
# To turn off transactions:
|
138
|
-
#
|
138
|
+
#
|
139
139
|
# class Vehicle < ActiveRecord::Base
|
140
140
|
# state_machine :initial => :parked, :use_transactions => false do
|
141
141
|
# ...
|
142
142
|
# end
|
143
143
|
# end
|
144
|
-
#
|
144
|
+
#
|
145
145
|
# == Validations
|
146
|
-
#
|
146
|
+
#
|
147
147
|
# As mentioned in StateMachines::Machine#state, you can define behaviors,
|
148
148
|
# like validations, that only execute for certain states. One *important*
|
149
149
|
# caveat here is that, due to a constraint in ActiveRecord's validation
|
150
150
|
# framework, custom validators will not work as expected when defined to run
|
151
151
|
# in multiple states. For example:
|
152
|
-
#
|
152
|
+
#
|
153
153
|
# class Vehicle < ActiveRecord::Base
|
154
154
|
# state_machine do
|
155
155
|
# ...
|
@@ -158,11 +158,11 @@ module StateMachines
|
|
158
158
|
# end
|
159
159
|
# end
|
160
160
|
# end
|
161
|
-
#
|
161
|
+
#
|
162
162
|
# In this case, the <tt>:speed_is_legal</tt> validation will only get run
|
163
163
|
# for the <tt>:second_gear</tt> state. To avoid this, you can define your
|
164
164
|
# custom validation like so:
|
165
|
-
#
|
165
|
+
#
|
166
166
|
# class Vehicle < ActiveRecord::Base
|
167
167
|
# state_machine do
|
168
168
|
# ...
|
@@ -171,124 +171,124 @@ module StateMachines
|
|
171
171
|
# end
|
172
172
|
# end
|
173
173
|
# end
|
174
|
-
#
|
174
|
+
#
|
175
175
|
# == Validation errors
|
176
|
-
#
|
176
|
+
#
|
177
177
|
# If an event fails to successfully fire because there are no matching
|
178
178
|
# transitions for the current record, a validation error is added to the
|
179
179
|
# record's state attribute to help in determining why it failed and for
|
180
180
|
# reporting via the UI.
|
181
|
-
#
|
181
|
+
#
|
182
182
|
# For example,
|
183
|
-
#
|
183
|
+
#
|
184
184
|
# vehicle = Vehicle.create(:state => 'idling') # => #<Vehicle id: 1, name: nil, state: "idling">
|
185
185
|
# vehicle.ignite # => false
|
186
186
|
# vehicle.errors.full_messages # => ["State cannot transition via \"ignite\""]
|
187
|
-
#
|
187
|
+
#
|
188
188
|
# If an event fails to fire because of a validation error on the record and
|
189
189
|
# *not* because a matching transition was not available, no error messages
|
190
190
|
# will be added to the state attribute.
|
191
|
-
#
|
191
|
+
#
|
192
192
|
# In addition, if you're using the <tt>ignite!</tt> version of the event,
|
193
193
|
# then the failure reason (such as the current validation errors) will be
|
194
194
|
# included in the exception that gets raised when the event fails. For
|
195
195
|
# example, assuming there's a validation on a field called +name+ on the class:
|
196
|
-
#
|
196
|
+
#
|
197
197
|
# vehicle = Vehicle.new
|
198
198
|
# vehicle.ignite! # => StateMachines::InvalidTransition: Cannot transition state via :ignite from :parked (Reason(s): Name cannot be blank)
|
199
|
-
#
|
199
|
+
#
|
200
200
|
# == Scopes
|
201
|
-
#
|
201
|
+
#
|
202
202
|
# To assist in filtering models with specific states, a series of named
|
203
203
|
# scopes are defined on the model for finding records with or without a
|
204
204
|
# particular set of states.
|
205
|
-
#
|
205
|
+
#
|
206
206
|
# These named scopes are essentially the functional equivalent of the
|
207
207
|
# following definitions:
|
208
|
-
#
|
208
|
+
#
|
209
209
|
# class Vehicle < ActiveRecord::Base
|
210
210
|
# named_scope :with_states, lambda {|*states| {:conditions => {:state => states}}}
|
211
211
|
# # with_states also aliased to with_state
|
212
|
-
#
|
212
|
+
#
|
213
213
|
# named_scope :without_states, lambda {|*states| {:conditions => ['state NOT IN (?)', states]}}
|
214
214
|
# # without_states also aliased to without_state
|
215
215
|
# end
|
216
|
-
#
|
216
|
+
#
|
217
217
|
# *Note*, however, that the states are converted to their stored values
|
218
218
|
# before being passed into the query.
|
219
|
-
#
|
219
|
+
#
|
220
220
|
# Because of the way named scopes work in ActiveRecord, they can be
|
221
221
|
# chained like so:
|
222
|
-
#
|
222
|
+
#
|
223
223
|
# Vehicle.with_state(:parked).all(:order => 'id DESC')
|
224
|
-
#
|
224
|
+
#
|
225
225
|
# Note that states can also be referenced by the string version of their
|
226
226
|
# name:
|
227
|
-
#
|
227
|
+
#
|
228
228
|
# Vehicle.with_state('parked')
|
229
|
-
#
|
229
|
+
#
|
230
230
|
# == Callbacks
|
231
|
-
#
|
231
|
+
#
|
232
232
|
# All before/after transition callbacks defined for ActiveRecord models
|
233
233
|
# behave in the same way that other ActiveRecord callbacks behave. The
|
234
234
|
# object involved in the transition is passed in as an argument.
|
235
|
-
#
|
235
|
+
#
|
236
236
|
# For example,
|
237
|
-
#
|
237
|
+
#
|
238
238
|
# class Vehicle < ActiveRecord::Base
|
239
239
|
# state_machine :initial => :parked do
|
240
240
|
# before_transition any => :idling do |vehicle|
|
241
241
|
# vehicle.put_on_seatbelt
|
242
242
|
# end
|
243
|
-
#
|
243
|
+
#
|
244
244
|
# before_transition do |vehicle, transition|
|
245
245
|
# # log message
|
246
246
|
# end
|
247
|
-
#
|
247
|
+
#
|
248
248
|
# event :ignite do
|
249
249
|
# transition :parked => :idling
|
250
250
|
# end
|
251
251
|
# end
|
252
|
-
#
|
252
|
+
#
|
253
253
|
# def put_on_seatbelt
|
254
254
|
# ...
|
255
255
|
# end
|
256
256
|
# end
|
257
|
-
#
|
257
|
+
#
|
258
258
|
# Note, also, that the transition can be accessed by simply defining
|
259
259
|
# additional arguments in the callback block.
|
260
|
-
#
|
260
|
+
#
|
261
261
|
# === Failure callbacks
|
262
|
-
#
|
262
|
+
#
|
263
263
|
# +after_failure+ callbacks allow you to execute behaviors when a transition
|
264
264
|
# is allowed, but fails to save. This could be useful for something like
|
265
265
|
# auditing transition attempts. Since callbacks run within transactions in
|
266
266
|
# ActiveRecord, a save failure will cause any records that get created in
|
267
267
|
# your callback to roll back. You can work around this issue like so:
|
268
|
-
#
|
268
|
+
#
|
269
269
|
# class TransitionLog < ActiveRecord::Base
|
270
270
|
# establish_connection Rails.env.to_sym
|
271
271
|
# end
|
272
|
-
#
|
272
|
+
#
|
273
273
|
# class Vehicle < ActiveRecord::Base
|
274
274
|
# state_machine do
|
275
275
|
# after_failure do |vehicle, transition|
|
276
276
|
# TransitionLog.create(:vehicle => vehicle, :transition => transition)
|
277
277
|
# end
|
278
|
-
#
|
278
|
+
#
|
279
279
|
# ...
|
280
280
|
# end
|
281
281
|
# end
|
282
|
-
#
|
282
|
+
#
|
283
283
|
# The +TransitionLog+ model establishes a second connection to the database
|
284
284
|
# that allows new records to be saved without being affected by rollbacks
|
285
285
|
# in the +Vehicle+ model's transaction.
|
286
|
-
#
|
286
|
+
#
|
287
287
|
# === Callback Order
|
288
|
-
#
|
288
|
+
#
|
289
289
|
# Callbacks occur in the following order. Callbacks specific to state_machine
|
290
290
|
# are bolded. The remaining callbacks are part of ActiveRecord.
|
291
|
-
#
|
291
|
+
#
|
292
292
|
# * (-) save
|
293
293
|
# * (-) begin transaction (if enabled)
|
294
294
|
# * (1) *before_transition*
|
@@ -304,9 +304,9 @@ module StateMachines
|
|
304
304
|
# * (8) *after_transition*
|
305
305
|
# * (-) end transaction (if enabled)
|
306
306
|
# * (9) after_commit
|
307
|
-
#
|
307
|
+
#
|
308
308
|
# == Observers
|
309
|
-
#
|
309
|
+
#
|
310
310
|
# In addition to support for ActiveRecord-like hooks, there is additional
|
311
311
|
# support for ActiveRecord observers. Because of the way ActiveRecord
|
312
312
|
# observers are designed, there is less flexibility around the specific
|
@@ -323,49 +323,49 @@ module StateMachines
|
|
323
323
|
# * before/after/after_failure_to-_transition_state_to_idling
|
324
324
|
# * before/after/after_failure_to-_transition_state
|
325
325
|
# * before/after/after_failure_to-_transition
|
326
|
-
#
|
326
|
+
#
|
327
327
|
# The following class shows an example of some of these hooks:
|
328
|
-
#
|
328
|
+
#
|
329
329
|
# class VehicleObserver < ActiveRecord::Observer
|
330
330
|
# def before_save(vehicle)
|
331
331
|
# # log message
|
332
332
|
# end
|
333
|
-
#
|
333
|
+
#
|
334
334
|
# # Callback for :ignite event *before* the transition is performed
|
335
335
|
# def before_ignite(vehicle, transition)
|
336
336
|
# # log message
|
337
337
|
# end
|
338
|
-
#
|
338
|
+
#
|
339
339
|
# # Callback for :ignite event *after* the transition has been performed
|
340
340
|
# def after_ignite(vehicle, transition)
|
341
341
|
# # put on seatbelt
|
342
342
|
# end
|
343
|
-
#
|
343
|
+
#
|
344
344
|
# # Generic transition callback *before* the transition is performed
|
345
345
|
# def after_transition(vehicle, transition)
|
346
346
|
# Audit.log(vehicle, transition)
|
347
347
|
# end
|
348
348
|
# end
|
349
|
-
#
|
349
|
+
#
|
350
350
|
# More flexible transition callbacks can be defined directly within the
|
351
351
|
# model as described in StateMachines::Machine#before_transition
|
352
352
|
# and StateMachines::Machine#after_transition.
|
353
|
-
#
|
353
|
+
#
|
354
354
|
# To define a single observer for multiple state machines:
|
355
|
-
#
|
355
|
+
#
|
356
356
|
# class StateMachineObserver < ActiveRecord::Observer
|
357
357
|
# observe Vehicle, Switch, Project
|
358
|
-
#
|
358
|
+
#
|
359
359
|
# def after_transition(record, transition)
|
360
360
|
# Audit.log(record, transition)
|
361
361
|
# end
|
362
362
|
# end
|
363
|
-
#
|
363
|
+
#
|
364
364
|
# == Internationalization
|
365
|
-
#
|
365
|
+
#
|
366
366
|
# In Rails 2.2+, any error message that is generated from performing invalid
|
367
367
|
# transitions can be localized. The following default translations are used:
|
368
|
-
#
|
368
|
+
#
|
369
369
|
# en:
|
370
370
|
# activerecord:
|
371
371
|
# errors:
|
@@ -375,19 +375,19 @@ module StateMachines
|
|
375
375
|
# invalid_event: "cannot transition when %{state}"
|
376
376
|
# # %{value} = attribute value, %{event} = Human event name, %{state} = Human current state name
|
377
377
|
# invalid_transition: "cannot transition via %{event}"
|
378
|
-
#
|
378
|
+
#
|
379
379
|
# Notice that the interpolation syntax is %{key} in Rails 3+. In Rails 2.x,
|
380
380
|
# the appropriate syntax is {{key}}.
|
381
|
-
#
|
381
|
+
#
|
382
382
|
# You can override these for a specific model like so:
|
383
|
-
#
|
383
|
+
#
|
384
384
|
# en:
|
385
385
|
# activerecord:
|
386
386
|
# errors:
|
387
387
|
# models:
|
388
388
|
# user:
|
389
389
|
# invalid: "is not valid"
|
390
|
-
#
|
390
|
+
#
|
391
391
|
# In addition to the above, you can also provide translations for the
|
392
392
|
# various states / events in each state machine. Using the Vehicle example,
|
393
393
|
# state translations will be looked for using the following keys, where
|
@@ -396,16 +396,16 @@ module StateMachines
|
|
396
396
|
# * <tt>activerecord.state_machines.#{model_name}.states.#{state_name}</tt>
|
397
397
|
# * <tt>activerecord.state_machines.#{machine_name}.states.#{state_name}</tt>
|
398
398
|
# * <tt>activerecord.state_machines.states.#{state_name}</tt>
|
399
|
-
#
|
399
|
+
#
|
400
400
|
# Event translations will be looked for using the following keys, where
|
401
401
|
# +model_name+ = "vehicle", +machine_name+ = "state" and +event_name+ = "ignite":
|
402
402
|
# * <tt>activerecord.state_machines.#{model_name}.#{machine_name}.events.#{event_name}</tt>
|
403
403
|
# * <tt>activerecord.state_machines.#{model_name}.events.#{event_name}</tt>
|
404
404
|
# * <tt>activerecord.state_machines.#{machine_name}.events.#{event_name}</tt>
|
405
405
|
# * <tt>activerecord.state_machines.events.#{event_name}</tt>
|
406
|
-
#
|
406
|
+
#
|
407
407
|
# An example translation configuration might look like so:
|
408
|
-
#
|
408
|
+
#
|
409
409
|
# es:
|
410
410
|
# activerecord:
|
411
411
|
# state_machines:
|
@@ -448,7 +448,16 @@ module StateMachines
|
|
448
448
|
end
|
449
449
|
|
450
450
|
def define_state_initializer
|
451
|
-
if ::ActiveRecord.gem_version >= Gem::Version.new('
|
451
|
+
if ::ActiveRecord.gem_version >= Gem::Version.new('5.0.0.alpha')
|
452
|
+
define_helper :instance, <<-end_eval, __FILE__, __LINE__ + 1
|
453
|
+
def initialize(attributes = nil)
|
454
|
+
super(attributes) do |*args|
|
455
|
+
self.class.state_machines.initialize_states(self, {}, attributes || {})
|
456
|
+
yield(*args) if block_given?
|
457
|
+
end
|
458
|
+
end
|
459
|
+
end_eval
|
460
|
+
elsif ::ActiveRecord.gem_version >= Gem::Version.new('4.2')
|
452
461
|
define_helper :instance, <<-end_eval, __FILE__, __LINE__ + 1
|
453
462
|
def initialize(attributes = nil, options = {})
|
454
463
|
super(attributes, options) do |*args|
|
@@ -491,12 +500,12 @@ module StateMachines
|
|
491
500
|
def save(*)
|
492
501
|
self.class.state_machine(#{name.inspect}).send(:around_save, self) { super }
|
493
502
|
end
|
494
|
-
|
503
|
+
|
495
504
|
def save!(*)
|
496
505
|
result = self.class.state_machine(#{name.inspect}).send(:around_save, self) { super }
|
497
506
|
result || raise(ActiveRecord::RecordInvalid.new(self))
|
498
507
|
end
|
499
|
-
|
508
|
+
|
500
509
|
def changed_for_autosave?
|
501
510
|
super || self.class.state_machines.any? {|name, machine| machine.action == :save && machine.read(self, :event)}
|
502
511
|
end
|
@@ -10,7 +10,7 @@ Gem::Specification.new do |spec|
|
|
10
10
|
spec.email = %w(terminale@gmail.com aaron@pluginaweek.org)
|
11
11
|
spec.summary = %q(State machines Active Record Integration)
|
12
12
|
spec.description = %q(Adds support for creating state machines for attributes on ActiveRecord)
|
13
|
-
spec.homepage = 'https://github.com/
|
13
|
+
spec.homepage = 'https://github.com/state-machines/state_machines-activerecord/'
|
14
14
|
spec.license = 'MIT'
|
15
15
|
|
16
16
|
spec.files = `git ls-files -z`.split("\x0")
|
@@ -18,7 +18,7 @@ Gem::Specification.new do |spec|
|
|
18
18
|
spec.require_paths = ['lib']
|
19
19
|
|
20
20
|
spec.add_dependency 'state_machines-activemodel', '>= 0.3.0'
|
21
|
-
spec.add_dependency 'activerecord' , '
|
21
|
+
spec.add_dependency 'activerecord' , '>=4.1', '<5.0'
|
22
22
|
spec.add_development_dependency 'rake', '~> 10.3'
|
23
23
|
spec.add_development_dependency 'sqlite3', '~> 1.3'
|
24
24
|
spec.add_development_dependency 'appraisal', '>= 1'
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: state_machines-activerecord
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.4.0.pre
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Abdelkader Boudih
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2015-
|
12
|
+
date: 2015-12-19 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: state_machines-activemodel
|
@@ -29,16 +29,22 @@ dependencies:
|
|
29
29
|
name: activerecord
|
30
30
|
requirement: !ruby/object:Gem::Requirement
|
31
31
|
requirements:
|
32
|
-
- - "
|
32
|
+
- - ">="
|
33
33
|
- !ruby/object:Gem::Version
|
34
34
|
version: '4.1'
|
35
|
+
- - "<"
|
36
|
+
- !ruby/object:Gem::Version
|
37
|
+
version: '5.0'
|
35
38
|
type: :runtime
|
36
39
|
prerelease: false
|
37
40
|
version_requirements: !ruby/object:Gem::Requirement
|
38
41
|
requirements:
|
39
|
-
- - "
|
42
|
+
- - ">="
|
40
43
|
- !ruby/object:Gem::Version
|
41
44
|
version: '4.1'
|
45
|
+
- - "<"
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '5.0'
|
42
48
|
- !ruby/object:Gem::Dependency
|
43
49
|
name: rake
|
44
50
|
requirement: !ruby/object:Gem::Requirement
|
@@ -126,6 +132,7 @@ files:
|
|
126
132
|
- Rakefile
|
127
133
|
- gemfiles/active_record_4.1.gemfile
|
128
134
|
- gemfiles/active_record_4.2.gemfile
|
135
|
+
- gemfiles/active_record_edge.gemfile
|
129
136
|
- lib/state_machines-activerecord.rb
|
130
137
|
- lib/state_machines/integrations/active_record.rb
|
131
138
|
- lib/state_machines/integrations/active_record/locale.rb
|
@@ -183,7 +190,7 @@ files:
|
|
183
190
|
- test/machine_without_transactions_test.rb
|
184
191
|
- test/model_test.rb
|
185
192
|
- test/test_helper.rb
|
186
|
-
homepage: https://github.com/
|
193
|
+
homepage: https://github.com/state-machines/state_machines-activerecord/
|
187
194
|
licenses:
|
188
195
|
- MIT
|
189
196
|
metadata: {}
|
@@ -198,12 +205,12 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
198
205
|
version: '0'
|
199
206
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
200
207
|
requirements:
|
201
|
-
- - "
|
208
|
+
- - ">"
|
202
209
|
- !ruby/object:Gem::Version
|
203
|
-
version:
|
210
|
+
version: 1.3.1
|
204
211
|
requirements: []
|
205
212
|
rubyforge_project:
|
206
|
-
rubygems_version: 2.4.
|
213
|
+
rubygems_version: 2.4.8
|
207
214
|
signing_key:
|
208
215
|
specification_version: 4
|
209
216
|
summary: State machines Active Record Integration
|
@@ -259,3 +266,4 @@ test_files:
|
|
259
266
|
- test/machine_without_transactions_test.rb
|
260
267
|
- test/model_test.rb
|
261
268
|
- test/test_helper.rb
|
269
|
+
has_rdoc:
|