state_shifter 0.7.1 → 0.7.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.
data/Gemfile CHANGED
@@ -6,6 +6,7 @@ source "http://rubygems.org"
6
6
  # Add dependencies to develop your gem here.
7
7
  # Include everything needed to run rake, tests, features, etc.
8
8
  group :development do
9
+ gem 'activerecord', '~> 3.2.x'
9
10
  gem "rspec", "~> 2.8.0"
10
11
  gem "yard", "~> 0.7"
11
12
  gem 'redcarpet'
data/Gemfile.lock CHANGED
@@ -1,8 +1,22 @@
1
1
  GEM
2
2
  remote: http://rubygems.org/
3
3
  specs:
4
+ activemodel (3.2.8)
5
+ activesupport (= 3.2.8)
6
+ builder (~> 3.0.0)
7
+ activerecord (3.2.8)
8
+ activemodel (= 3.2.8)
9
+ activesupport (= 3.2.8)
10
+ arel (~> 3.0.2)
11
+ tzinfo (~> 0.3.29)
12
+ activesupport (3.2.8)
13
+ i18n (~> 0.6)
14
+ multi_json (~> 1.0)
15
+ arel (3.0.2)
16
+ builder (3.0.0)
4
17
  diff-lcs (1.1.3)
5
18
  git (1.2.5)
19
+ i18n (0.6.0)
6
20
  jeweler (1.8.4)
7
21
  bundler (~> 1.0)
8
22
  git (>= 1.2.5)
@@ -26,12 +40,14 @@ GEM
26
40
  multi_json (~> 1.0)
27
41
  simplecov-html (~> 0.5.3)
28
42
  simplecov-html (0.5.3)
43
+ tzinfo (0.3.33)
29
44
  yard (0.8.2.1)
30
45
 
31
46
  PLATFORMS
32
47
  ruby
33
48
 
34
49
  DEPENDENCIES
50
+ activerecord (~> 3.2.x)
35
51
  bundler (~> 1.1.0)
36
52
  jeweler (~> 1.8.4)
37
53
  rdoc (~> 3.12)
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.7.1
1
+ 0.7.2
@@ -0,0 +1,97 @@
1
+ class Advanced
2
+ include StateShifter::Definition
3
+
4
+ ###
5
+
6
+ state_machine do
7
+
8
+ state :initialized do
9
+
10
+ event :start_date_changed, :call => :handle_start_date_changed
11
+ event :forced_start => :running
12
+ event :start_date_reached => :running, :if => :start_date_reached?
13
+ event :abort_initialized_contest => :finalized
14
+ end
15
+
16
+ state :running do
17
+
18
+ on_entry do |previous_state, trigger_event|
19
+ running_entry previous_state, trigger_event
20
+ end
21
+
22
+ event :abort_running_contest => :notify_stakeholders
23
+ event :changed_properties
24
+ event :keep_users_engaged
25
+ event :deadline_reached => :notify_organizers, :if => :entries_deadline_reached?
26
+ event :spots_filled => :notify_organizers, :if => :spots_filled?
27
+ event :deadline_reached_without_approvals => :notify_pending_users, :if => :entries_deadline_reached_without_approvals?
28
+ event :deadline_reached_without_entries => :finalized, :if => :entries_deadline_reached_without_entries?
29
+ end
30
+
31
+ state :notify_organizers do
32
+ on_entry :send_notification_to_organizers
33
+ event :organizers_notified => :awaiting_organizer_reply
34
+ end
35
+
36
+ state :awaiting_organizer_reply do
37
+ event :organizer_confirmation_missing => :notify_stakeholders, :if => :organizer_confirmation_deadline_reached?
38
+ event :keep_organizers_engaged
39
+ event :organizer_confirmation_received => :notify_approved_users
40
+ event :organizer_has_more_tickets => :running
41
+ end
42
+
43
+ state :notify_stakeholders do
44
+ on_entry :send_notification_to_stakeholders
45
+ event :stakeholders_notified => :cancelled
46
+ end
47
+
48
+ state :cancelled
49
+
50
+ state :notify_pending_users do
51
+ on_entry :send_notification_to_pending_users
52
+ event :pending_users_notified => :finalized
53
+ end
54
+
55
+ state :notify_approved_users do
56
+ on_entry :send_notification_to_approved_users
57
+ event :approved_users_notified => :send_list_to_organizers
58
+ end
59
+
60
+ state :send_list_to_organizers do
61
+ on_entry :send_guestlist_to_organizers
62
+ event :list_sent_to_organizers => :awaiting_attendance
63
+ end
64
+
65
+ state :awaiting_attendance do
66
+ event :remind_to_fill_in_report => :create_report_filling_requests
67
+ end
68
+
69
+ state :create_report_filling_requests do
70
+ on_entry :send_report_filling_requests
71
+ event :finalize => :finalized
72
+ end
73
+
74
+ state :finalized
75
+
76
+ on_transition do |from,to,trigger_event, duration|
77
+ benchmark from, to, trigger_event, duration
78
+ end
79
+ end
80
+
81
+ persist_attribute :lollies
82
+
83
+ ###
84
+
85
+ def entries_deadline_reached?
86
+ true
87
+ end
88
+
89
+ def running_entry previous_state, trigger_event
90
+ #
91
+ end
92
+
93
+ def benchmark from, to, trigger_event, duration
94
+ #
95
+ end
96
+
97
+ end
@@ -2,9 +2,15 @@ module StateShifter
2
2
  module Definition
3
3
  module ClassMethods
4
4
 
5
- attr_accessor :state_machine_definition
5
+ attr_accessor :state_machine_definition, :persist_attr_name
6
+
7
+ def persist_attribute attr_name
8
+ raise ::StateShifter::PersistenceAttributeAlreadyDefined if @persist_attr_name
9
+ @persist_attr_name = attr_name.to_sym
10
+ end
6
11
 
7
12
  def state_machine &definition
13
+ @persist_attr_name ||= :current_state
8
14
  @state_machine_definition = Contents.new(&definition)
9
15
 
10
16
  @state_machine_definition.states.each do |state_name, state_definition|
@@ -18,7 +24,7 @@ module StateShifter
18
24
 
19
25
  state_machine_definition.get(:state, from_state).events.each do |event_name, event_def|
20
26
  if event_def.has_guards? && check_guards
21
- next if @subject.send(:check_guards, event_name).is_a?(Array)
27
+ next if self.send(:check_guards, event_name).is_a?(Array)
22
28
  end
23
29
 
24
30
  next_states_hash.merge!( event_def.to.nil? ? { from_state.to_sym => event_name } : { event_def.to => event_def.name } )
@@ -1,7 +1,5 @@
1
1
  module StateShifter
2
-
3
2
  module Definition
4
-
5
3
  class Contents
6
4
 
7
5
  attr_accessor :states, :initial_state, :events, :on_transition_proc
@@ -61,6 +59,12 @@ module StateShifter
61
59
  end
62
60
  end
63
61
 
62
+ def on_transition &proc_contents
63
+ @on_transition_proc = proc_contents
64
+ end
65
+
66
+ ### end of DSL methods
67
+
64
68
  def get key, what
65
69
  case key
66
70
  when :event
@@ -70,16 +74,10 @@ module StateShifter
70
74
  end
71
75
  end
72
76
 
73
- def on_transition &proc_contents
74
- @on_transition_proc = proc_contents
75
- end
76
-
77
77
  def has_on_transition_proc?
78
78
  !@on_transition_proc.nil?
79
79
  end
80
80
 
81
81
  end
82
-
83
82
  end
84
-
85
83
  end
@@ -1,14 +1,17 @@
1
1
  module StateShifter
2
-
3
2
  module Definition
4
-
5
3
  module InstanceMethods
6
4
 
7
- attr_accessor :current_state, :state_machine_definition
5
+ def current_state
6
+ @current_state ||= get_current_state
7
+ end
8
8
 
9
- def initialize
10
- @current_state = state_machine_definition.initial_state.name.to_sym
11
- @subject = self
9
+ def get_current_state
10
+ instance_variable_defined?(:@current_state) ? @current_state : state_machine_definition.initial_state.name.to_sym
11
+ end
12
+
13
+ def set_current_state value
14
+ @current_state = value
12
15
  end
13
16
 
14
17
  def state_machine_definition
@@ -42,14 +45,14 @@ module StateShifter
42
45
  def check_event_callbacks event_name
43
46
  event_def = state_machine_definition.get(:event, event_name)
44
47
  begin
45
- @subject.send event_def.callback
48
+ self.send event_def.callback
46
49
  rescue NoMethodError
47
50
  raise ::StateShifter::CallbackMethodNotDefined, event_def.callback
48
51
  end
49
52
  end
50
53
 
51
54
  def current_state_def
52
- state_machine_definition.get(:state, @current_state)
55
+ state_machine_definition.get(:state, current_state)
53
56
  end
54
57
 
55
58
  def call_state_entry_callback trigger, old_state
@@ -57,12 +60,12 @@ module StateShifter
57
60
 
58
61
  if proc_or_method_name.is_a?(Symbol)
59
62
  begin
60
- @subject.send proc_or_method_name
63
+ self.send proc_or_method_name
61
64
  rescue NoMethodError
62
65
  raise ::StateShifter::CallbackMethodNotDefined, proc_or_method_name
63
66
  end
64
67
  else
65
- @subject.instance_exec(old_state, trigger.to_sym, &proc_or_method_name)
68
+ self.instance_exec(old_state, trigger.to_sym, &proc_or_method_name)
66
69
  end
67
70
  end
68
71
 
@@ -70,15 +73,16 @@ module StateShifter
70
73
  _start = Time.now
71
74
 
72
75
  # BOOP!
73
- old_state = @current_state
74
- @current_state = args[:to].to_sym
76
+ old_state = current_state
77
+ set_current_state args[:to].to_sym
75
78
  #
76
79
 
77
80
  check_event_callbacks(args[:trigger]) if state_machine_definition.get(:event, args[:trigger]).has_callback?
78
81
 
79
82
  call_state_entry_callback(args[:trigger], old_state) if current_state_def.has_entry_callback?
80
83
 
81
- @subject.instance_exec(old_state, @current_state, args[:trigger].to_sym, (Time.now - _start), &state_machine_definition.on_transition_proc) if state_machine_definition.has_on_transition_proc?
84
+ self.instance_exec(old_state, current_state, args[:trigger].to_sym, (Time.now - _start), &state_machine_definition.on_transition_proc) if state_machine_definition.has_on_transition_proc?
85
+
82
86
  true
83
87
  end
84
88
 
@@ -105,5 +109,4 @@ module StateShifter
105
109
 
106
110
  end
107
111
  end
108
-
109
112
  end
data/lib/state_shifter.rb CHANGED
@@ -4,9 +4,6 @@ require 'state_shifter/definition'
4
4
  require 'state_shifter/definition/contents'
5
5
  require 'state_shifter/definition/class_methods'
6
6
  require 'state_shifter/definition/instance_methods'
7
- require 'state_shifter/mountable'
8
- require 'state_shifter/mountable/class_methods'
9
- require 'state_shifter/mountable/instance_methods'
10
7
 
11
8
  class ::StateShifter::TransitionHalted < Exception ; end
12
9
  class ::StateShifter::GuardMethodUndefined < Exception ; end
@@ -14,4 +11,5 @@ class ::StateShifter::GuardNotSatisfied < Exception ; end
14
11
  class ::StateShifter::CallbackMethodNotDefined < Exception ; end
15
12
  class ::StateShifter::RedifiningEvent < Exception ; end
16
13
  class ::StateShifter::RedifiningState < Exception ; end
14
+ class ::StateShifter::PersistenceAttributeAlreadyDefined < Exception ; end
17
15
 
data/spec/spec_helper.rb CHANGED
@@ -1,10 +1,14 @@
1
1
  $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
2
2
  $LOAD_PATH.unshift(File.dirname(__FILE__))
3
+
3
4
  require 'rspec'
5
+ require 'active_record'
6
+
4
7
  require 'state_shifter'
5
- require 'simplecov'
6
8
 
7
9
  if ENV['COVERAGE']
10
+ require 'simplecov'
11
+
8
12
  SimpleCov.start do
9
13
  add_filter 'spec'
10
14
  end
@@ -1,7 +1,6 @@
1
1
  require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
2
  require_relative '../examples/simple'
3
3
  require_relative '../examples/advanced'
4
- require_relative '../examples/mounted'
5
4
 
6
5
  shared_examples_for 'a simple state machine' do
7
6
 
@@ -101,12 +100,6 @@ describe Simple do
101
100
 
102
101
  end
103
102
 
104
- describe Mounted do
105
-
106
- it_should_behave_like 'a simple state machine'
107
-
108
- end
109
-
110
103
  describe 'Malformed state machines' do
111
104
 
112
105
  it 'should complain about redifining states' do
@@ -117,6 +110,18 @@ describe 'Malformed state machines' do
117
110
  lambda { require_relative '../examples/malformed_events' }.should raise_error(StateShifter::RedifiningEvent, 'submit')
118
111
  end
119
112
 
113
+ it 'should complain when the persistence attribute is set after the state machine definition' do
114
+ lambda { require_relative '../examples/malformed_persistence' }.should raise_error(StateShifter::PersistenceAttributeAlreadyDefined)
115
+ end
116
+
117
+ end
118
+
119
+ describe 'Advanced state machine functionality' do
120
+
121
+ before(:each) do
122
+ @advanced = Advanced.new
123
+ end
124
+
120
125
  it 'should complain about undefined guards' do
121
126
  advanced = Advanced.new
122
127
  lambda { advanced.can_start_date_reached?}.should raise_error(StateShifter::GuardMethodUndefined, 'start_date_reached?')
@@ -129,14 +134,6 @@ describe 'Malformed state machines' do
129
134
  lambda { advanced.deadline_reached }.should raise_error(StateShifter::CallbackMethodNotDefined, 'send_notification_to_organizers')
130
135
  end
131
136
 
132
- end
133
-
134
- describe 'Advanced state machine functionality' do
135
-
136
- before(:each) do
137
- @advanced = Advanced.new
138
- end
139
-
140
137
  it 'should complain about looping event callbacks not being defined' do
141
138
  lambda { @advanced.start_date_changed }.should raise_error(StateShifter::CallbackMethodNotDefined, 'handle_start_date_changed')
142
139
  end
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = "state_shifter"
8
- s.version = "0.7.1"
8
+ s.version = "0.7.2"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Bruno Antunes"]
12
- s.date = "2012-08-24"
12
+ s.date = "2012-08-27"
13
13
  s.description = "state_shifter is a gem that adds state machine behavior to a class"
14
14
  s.email = "sardaukar.siet@gmail.com"
15
15
  s.extra_rdoc_files = [
@@ -27,8 +27,8 @@ Gem::Specification.new do |s|
27
27
  "VERSION",
28
28
  "examples/advanced.rb",
29
29
  "examples/malformed_events.rb",
30
+ "examples/malformed_persistence.rb",
30
31
  "examples/malformed_states.rb",
31
- "examples/mounted.rb",
32
32
  "examples/simple.rb",
33
33
  "lib/state_shifter.rb",
34
34
  "lib/state_shifter/definition.rb",
@@ -36,9 +36,6 @@ Gem::Specification.new do |s|
36
36
  "lib/state_shifter/definition/contents.rb",
37
37
  "lib/state_shifter/definition/instance_methods.rb",
38
38
  "lib/state_shifter/event.rb",
39
- "lib/state_shifter/mountable.rb",
40
- "lib/state_shifter/mountable/class_methods.rb",
41
- "lib/state_shifter/mountable/instance_methods.rb",
42
39
  "lib/state_shifter/state.rb",
43
40
  "spec/spec_helper.rb",
44
41
  "spec/state_shifter_spec.rb",
@@ -54,6 +51,7 @@ Gem::Specification.new do |s|
54
51
  s.specification_version = 3
55
52
 
56
53
  if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
54
+ s.add_development_dependency(%q<activerecord>, ["~> 3.2.x"])
57
55
  s.add_development_dependency(%q<rspec>, ["~> 2.8.0"])
58
56
  s.add_development_dependency(%q<yard>, ["~> 0.7"])
59
57
  s.add_development_dependency(%q<redcarpet>, [">= 0"])
@@ -62,6 +60,7 @@ Gem::Specification.new do |s|
62
60
  s.add_development_dependency(%q<jeweler>, ["~> 1.8.4"])
63
61
  s.add_development_dependency(%q<simplecov>, [">= 0"])
64
62
  else
63
+ s.add_dependency(%q<activerecord>, ["~> 3.2.x"])
65
64
  s.add_dependency(%q<rspec>, ["~> 2.8.0"])
66
65
  s.add_dependency(%q<yard>, ["~> 0.7"])
67
66
  s.add_dependency(%q<redcarpet>, [">= 0"])
@@ -71,6 +70,7 @@ Gem::Specification.new do |s|
71
70
  s.add_dependency(%q<simplecov>, [">= 0"])
72
71
  end
73
72
  else
73
+ s.add_dependency(%q<activerecord>, ["~> 3.2.x"])
74
74
  s.add_dependency(%q<rspec>, ["~> 2.8.0"])
75
75
  s.add_dependency(%q<yard>, ["~> 0.7"])
76
76
  s.add_dependency(%q<redcarpet>, [">= 0"])
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: state_shifter
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.7.1
4
+ version: 0.7.2
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,8 +9,24 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2012-08-24 00:00:00.000000000 Z
12
+ date: 2012-08-27 00:00:00.000000000 Z
13
13
  dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: activerecord
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ~>
20
+ - !ruby/object:Gem::Version
21
+ version: 3.2.x
22
+ type: :development
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ~>
28
+ - !ruby/object:Gem::Version
29
+ version: 3.2.x
14
30
  - !ruby/object:Gem::Dependency
15
31
  name: rspec
16
32
  requirement: !ruby/object:Gem::Requirement
@@ -141,8 +157,8 @@ files:
141
157
  - VERSION
142
158
  - examples/advanced.rb
143
159
  - examples/malformed_events.rb
160
+ - examples/malformed_persistence.rb
144
161
  - examples/malformed_states.rb
145
- - examples/mounted.rb
146
162
  - examples/simple.rb
147
163
  - lib/state_shifter.rb
148
164
  - lib/state_shifter/definition.rb
@@ -150,9 +166,6 @@ files:
150
166
  - lib/state_shifter/definition/contents.rb
151
167
  - lib/state_shifter/definition/instance_methods.rb
152
168
  - lib/state_shifter/event.rb
153
- - lib/state_shifter/mountable.rb
154
- - lib/state_shifter/mountable/class_methods.rb
155
- - lib/state_shifter/mountable/instance_methods.rb
156
169
  - lib/state_shifter/state.rb
157
170
  - spec/spec_helper.rb
158
171
  - spec/state_shifter_spec.rb
@@ -172,7 +185,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
172
185
  version: '0'
173
186
  segments:
174
187
  - 0
175
- hash: -1507395421623075771
188
+ hash: -2788732275758639550
176
189
  required_rubygems_version: !ruby/object:Gem::Requirement
177
190
  none: false
178
191
  requirements:
data/examples/mounted.rb DELETED
@@ -1,8 +0,0 @@
1
- require_relative 'simple'
2
-
3
- class Mounted
4
- include StateShifter::Mountable
5
-
6
- mount_state_machine Simple
7
-
8
- end
@@ -1,13 +0,0 @@
1
- module StateShifter
2
- module Mountable
3
- module ClassMethods
4
-
5
- attr_accessor :mountable_class_name
6
-
7
- def mount_state_machine mountable_class_name
8
- self.mountable_class_name = mountable_class_name
9
- end
10
-
11
- end
12
- end
13
- end
@@ -1,20 +0,0 @@
1
- module StateShifter
2
- module Mountable
3
- module InstanceMethods
4
-
5
- attr_accessor :state_machine_definition
6
-
7
- def initialize
8
- @state_machine_definition = self.class.mountable_class_name.new
9
- @state_machine_definition.instance_variable_set(:@subject,self)
10
-
11
- ( @state_machine_definition.methods - Object.methods).sort.each do |meth|
12
- self.class.send :define_method, meth, &@state_machine_definition.method(meth)
13
- end
14
-
15
- super
16
- end
17
-
18
- end
19
- end
20
- end
@@ -1,10 +0,0 @@
1
- module StateShifter
2
- module Mountable
3
-
4
- def self.included klass
5
- klass.send :include, InstanceMethods
6
- klass.extend ClassMethods
7
- end
8
-
9
- end
10
- end