使用来自Piotr Murach的Ruby finite machine gem。
想要以持久(存储)状态恢复状态机。该文档教授初始状态,并从ActiveRecord模型恢复状态。
我能找到的只是让我定义初始状态的DSL,或定义转换到初始状态的事件。两者都要求我在编码时定义初始状态。
fm = FiniteMachine.define do
initial :red
或
fm = FiniteMachine.define do
events {
event :start, :none => :red
在实践中,我正在定义一个“独立”的行,
class Engine < FiniteMachine::Definition
initial :neutral
我想要的是在该类的初始值设定项中定义初始状态,如:
class Engine < FiniteMachine::Definition
def initialize(car, state)
initial state
target car
end
然而,这不起作用。初始化后,我将:none
作为当前状态。
找到restore!
方法和文档中有关使用ActiveRecord保持状态的部分。尝试过以下几点:
class Engine < FiniteMachine::Definition
def initialize(car, state)
restore! state
target car
end
然而,构造函数在其上调用FiniteMachine::StateMachine
时返回类new
。 new
方法接受任意数量的参数,并且永远不会调用类的任何initialize
方法。它返回一个不同的类。
以下是该程序的输出:
GSM class is FiniteMachine::StateMachine
GSM current state is red
.gems/gems/finite_machine-0.10.1/lib/finite_machine/state_machine.rb:259:in `valid_state?': inappropriate current state 'red' (FiniteMachine::InvalidStateError)
该计划:
require 'finite_machine'
class GenericStateMachine < FiniteMachine::Definition
initial :red
def initialize(light)
puts "INITIALIZER WITH #{light}"
super
restore! light.state
target light
end
events {
event :start, :red => :green
event :stop, :green => :red
}
callbacks {
on_enter { |event| target.state = event.to }
}
end
class Light
attr_accessor :state
def initialize
state = 'green'
end
def to_s
"Light in state #{state}"
end
end
light = Light.new
gsm = GenericStateMachine.new(light)
puts "GSM class is #{gsm.class.to_s}"
puts "GSM current state is #{gsm.current}"
gsm.stop
puts "GSM state after stop is #{gsm.current}"
puts "Light state after stop is #{light.state}"
答案 0 :(得分:1)
更好的方法是创建一个状态机factory method,它通过FiniteMachine.define
使用DSL
以下是该程序的输出:
CREATING MACHINE with Light in state green
GSM class is FiniteMachine::StateMachine
GSM current state is green
GSM state after stop is red
Light state after stop is red
该计划:
require 'finite_machine'
class LightMachineFactory
def self.create_machine(light)
FiniteMachine.define do
puts "CREATING MACHINE with #{light}"
initial light.state
target light
events {
event :start, :red => :green
event :stop, :green => :red
}
callbacks {
on_enter { |event| target.state = event.to }
}
end
end
end
class Light
attr_accessor :state
def initialize
@state = 'green'
end
def to_s
"Light in state #{state}"
end
def state
@state.to_sym
end
end
light = Light.new
gsm = LightMachineFactory.create_machine(light)
puts "GSM class is #{gsm.class.to_s}"
puts "GSM current state is #{gsm.current}"
gsm.stop
puts "GSM state after stop is #{gsm.current}"
puts "Light state after stop is #{light.state}"
此内容由Gem的Github源代码库中的(my)closed issue共享。 (对于更多的使用问题而不是问题,这是一个更好的论坛。)