Skip to content

Commit

Permalink
Change any state to be a unique object to prevet collision with user …
Browse files Browse the repository at this point in the history
…defined state name in ref issue #44
  • Loading branch information
piotrmurach committed Oct 30, 2018
1 parent 191413a commit c0e4904
Show file tree
Hide file tree
Showing 13 changed files with 43 additions and 36 deletions.
10 changes: 5 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -525,21 +525,21 @@ fm = FiniteMachine.define do
end
```

### 2.5 From :any state
### 2.4 From `any_state`

The **FiniteMachine** offers few ways to transition out of any state. This is particularly useful when the machine already defines many states.

You can pass `:any` for the name of the state, for instance:
You can use `any_state` for the name of the state, for instance:

```ruby
event :run, from: :any, to: :green
event :run, from: any_state, to: :green

or

event :run, :any => :green
event :run, any_state => :green
```

Alternatively, you can skip the `:any` state definition and just specify `to` state:
Alternatively, you can skip the `any_state` call and just specify `to` state:

```ruby
event :run, to: :green
Expand Down
7 changes: 4 additions & 3 deletions lib/finite_machine.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

require 'logger'

require_relative 'finite_machine/const'
require_relative 'finite_machine/logger'
require_relative 'finite_machine/definition'
require_relative 'finite_machine/state_machine'
Expand All @@ -14,11 +15,11 @@ module FiniteMachine
# Initial default event name
DEFAULT_EVENT_NAME = :init

# Describe any state transition
ANY_STATE = :any
# Describe any transition state
ANY_STATE = Const.new(:any)

# Describe any event name
ANY_EVENT = :any_event
ANY_EVENT = Const.new(:any_event)

# When transition between states is invalid
TransitionError = Class.new(::StandardError)
Expand Down
12 changes: 12 additions & 0 deletions lib/finite_machine/dsl.rb
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,18 @@ def initialize(machine, attrs = {})
@machine = machine
end

# Expose any state constant
# @api public
def any_state
ANY_STATE
end

# Expose any event constant
# @api public
def any_event
ANY_EVENT
end

# Delegate attributes to machine instance
#
# @api private
Expand Down
2 changes: 1 addition & 1 deletion lib/finite_machine/observer.rb
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@

module FiniteMachine
# A class responsible for observing state changes
class Observer
class Observer < GenericDSL
include Threadable
include Safety

Expand Down
4 changes: 2 additions & 2 deletions spec/integration/system_spec.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# encoding: utf-8
# frozen_string_literal: true

RSpec.describe FiniteMachine, 'system' do

Expand All @@ -7,7 +7,7 @@
stub_const("FSM_A", Class.new(FiniteMachine::Definition) do
events {
event :init, :none => :green
event :green, :any => :green
event :green, any_state => :green
}
callbacks {
on_before do |event|
Expand Down
6 changes: 3 additions & 3 deletions spec/unit/callbacks_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
on_exit do |event| called << 'on_exit' end

# generic event callbacks
on_before do |event| called << 'on_before' end
on_before any_event do |event| called << 'on_before' end
on_after do |event| called << 'on_after' end

# state callbacks
Expand Down Expand Up @@ -334,7 +334,7 @@
initial :green

events {
event :slow, [:red, :blue, :green] => :yellow
event :slow, [:red, :blue, :green] => :yellow
event :fast, :red => :purple
}

Expand Down Expand Up @@ -447,7 +447,7 @@

events {
event :power_on, :off => :red
event :power_off, :any => :off
event :power_off, any_state => :off
event :go, :red => :green
event :slow, :green => :yellow
event :stop, :yellow => :red
Expand Down
8 changes: 3 additions & 5 deletions spec/unit/choice_spec.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
# encoding: utf-8

require 'spec_helper'
# frozen_string_literal: true

RSpec.describe FiniteMachine, '#choice' do
before(:each) {
Expand Down Expand Up @@ -157,7 +155,7 @@ def promo?(token = false)
fsm = FiniteMachine.define do
initial :red

event :go, from: :any do
event :go, from: any_state do
choice :pink, if: -> { false }
choice :green
end
Expand Down Expand Up @@ -283,7 +281,7 @@ def promo?(token = false)
choice :yellow
end

event :finish, from: :any do
event :finish, from: any_state do
choice :green, if: -> { false }
choice :red
end
Expand Down
12 changes: 5 additions & 7 deletions spec/unit/events_spec.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
# encoding: utf-8

require 'spec_helper'
# frozen_string_literal: true

RSpec.describe FiniteMachine, 'events' do

Expand Down Expand Up @@ -76,7 +74,7 @@
expect(fsm.cannot?(:slow)).to be true
end

it "permits event from any state with :any 'from'" do
it "permits event from any state using :from" do
fsm = FiniteMachine.define do
initial :green

Expand All @@ -85,7 +83,7 @@
event :stop, from: :yellow, to: :red
event :ready, from: :red, to: :yellow
event :go, from: :yellow, to: :green
event :run, from: :any, to: :green
event :run, from: any_state, to: :green
}
end

Expand Down Expand Up @@ -119,7 +117,7 @@
event :start, :red => :yellow
event :run, :yellow => :green
event :stop, :green => :red
event :go, :any => :green
event :go, any_state => :green
}
end

Expand Down Expand Up @@ -382,7 +380,7 @@
events {
event :start, :neutral => :engine_on
event :drive, :engine_on => :running, if: -> { return false }
event :stop, :any => :neutral
event :stop, any_state => :neutral
}

callbacks {
Expand Down
4 changes: 2 additions & 2 deletions spec/unit/hook_event/infer_default_name_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,11 @@
RSpec.describe FiniteMachine::HookEvent, '#infer_default_name' do
it "infers default name for state" do
hook_event = described_class::Enter
expect(described_class.infer_default_name(hook_event)).to eq(:any)
expect(described_class.infer_default_name(hook_event)).to eq(FiniteMachine::ANY_STATE)
end

it "infers default name for event" do
hook_event = described_class::Before
expect(described_class.infer_default_name(hook_event)).to eq(:any_event)
expect(described_class.infer_default_name(hook_event)).to eq(FiniteMachine::ANY_EVENT)
end
end
4 changes: 2 additions & 2 deletions spec/unit/if_unless_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ def pending?
events {
event :go, :red => :green,
if: proc { |context| called << "cond_red_green(#{context})"; true}
event :stop, from: :any do
event :stop, from: any_state do
choice :red,
if: proc { |context| called << "cond_any_red(#{context})"; true }
end
Expand Down Expand Up @@ -64,7 +64,7 @@ def pending?
events {
event :go, :red => :green,
if: proc { |_, a| called << "cond_red_green(#{a})"; true }
event :stop, from: :any do
event :stop, from: any_state do
choice :red,
if: proc { |_, b| called << "cond_any_red(#{b})"; true }
end
Expand Down
2 changes: 1 addition & 1 deletion spec/unit/state_parser/parse_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@
let(:attrs) { { to: :green }}

it "inserts :any from state" do
expect(object.parse(attrs)).to eq({any: :green})
expect(object.parse(attrs)).to eq({FiniteMachine::ANY_STATE => :green})
end
end

Expand Down
2 changes: 1 addition & 1 deletion spec/unit/transition/matches_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
end

it "matches any state" do
states = {:any => :red}
states = {FiniteMachine::ANY_STATE => :red}
transition = described_class.new(machine, states: states)

expect(transition.matches?(:green)).to eq(true)
Expand Down
6 changes: 2 additions & 4 deletions spec/unit/transition/to_state_spec.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
# encoding: utf-8

require 'spec_helper'
# frozen_string_literal: true

RSpec.describe FiniteMachine::Transition, '.to_state' do
let(:machine) { double(:machine) }
Expand All @@ -13,7 +11,7 @@
end

it "finds to state for transition from any state" do
states = {:any => :red}
states = {FiniteMachine::ANY_STATE => :red}
transition = described_class.new(machine, states: states)

expect(transition.to_state(:green)).to eq(:red)
Expand Down

0 comments on commit c0e4904

Please sign in to comment.