decide.rb 0.3.0 → 0.4.1
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/CHANGELOG.md +8 -0
- data/examples/decide.md +58 -0
- data/examples/evolve.md +39 -0
- data/lib/decider/version.rb +1 -1
- data/lib/decider.rb +31 -27
- metadata +1 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: bde47991ca269c4a20a47e138fb8eeb5d1135262a390991bb4b946daa778362d
|
4
|
+
data.tar.gz: 5c3712f51013003b099ee4e3f7a568adecd92b0cd5d988c2f4140bb578f88e0c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ae016ee97e995c8338221555a0cd444aa600a6ff2e22fa83e53fe2743747dca391392b07d032a3100cce9240978cd0605f86fb355692d0938bf0fd34560c8222
|
7
|
+
data.tar.gz: 97ca74eb8729f4fbd1fdfe86e545cb428ef58974cfc7b91645ea246f0db140e0432229e2bec5e686898dd4a365e36419ea8dfd6ca903d643a6524c4db470380d
|
data/CHANGELOG.md
CHANGED
data/examples/decide.md
CHANGED
@@ -21,3 +21,61 @@ Raise error when using `decide!`:
|
|
21
21
|
decider.decide! :unknown, decider.initial_state
|
22
22
|
#> raise ArgumentError, Unknown command
|
23
23
|
```
|
24
|
+
|
25
|
+
## Commands
|
26
|
+
|
27
|
+
Commands can be primitives like symbols:
|
28
|
+
|
29
|
+
```ruby
|
30
|
+
decider = Decider.define do
|
31
|
+
initial_state :initial
|
32
|
+
|
33
|
+
decide :start do |command, state|
|
34
|
+
case state
|
35
|
+
in :initial, :stopped
|
36
|
+
[:started]
|
37
|
+
else
|
38
|
+
[]
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
decide :stop do |command, state|
|
43
|
+
case state
|
44
|
+
in :started
|
45
|
+
[:stopped]
|
46
|
+
else
|
47
|
+
[]
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
```
|
52
|
+
|
53
|
+
Or any classes like [Dry::Struct](https://dry-rb.org/gems/dry-struct/) or [Data](https://rubyapi.org/3.3/o/data):
|
54
|
+
|
55
|
+
```ruby
|
56
|
+
Start = Data.define(:value)
|
57
|
+
Stop = Data.define
|
58
|
+
|
59
|
+
decider = Decider.define do
|
60
|
+
initial_state :initial
|
61
|
+
|
62
|
+
decide Start do |command, state|
|
63
|
+
case state
|
64
|
+
in :initial, :stopped
|
65
|
+
[:started, command.value]
|
66
|
+
else
|
67
|
+
[]
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
decide Stop do |command, state|
|
72
|
+
case state
|
73
|
+
in :started
|
74
|
+
[:stopped]
|
75
|
+
else
|
76
|
+
[]
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
80
|
+
```
|
81
|
+
|
data/examples/evolve.md
CHANGED
@@ -21,3 +21,42 @@ Raise error when using `evolve!`:
|
|
21
21
|
decider.evolve! decider.initial_state, :unknown
|
22
22
|
#> raise ArgumentError, Unknown event
|
23
23
|
```
|
24
|
+
|
25
|
+
## Events
|
26
|
+
|
27
|
+
Events can be primitives like symbols:
|
28
|
+
|
29
|
+
```ruby
|
30
|
+
decider = Decider.define do
|
31
|
+
initial_state :initial
|
32
|
+
|
33
|
+
evolve :started do |state, event|
|
34
|
+
:started
|
35
|
+
end
|
36
|
+
|
37
|
+
evolve :stopped do |state, event|
|
38
|
+
:stopped
|
39
|
+
end
|
40
|
+
end
|
41
|
+
```
|
42
|
+
|
43
|
+
Or any classes like [Dry::Struct](https://dry-rb.org/gems/dry-struct/) or [Data](https://rubyapi.org/3.3/o/data):
|
44
|
+
|
45
|
+
```ruby
|
46
|
+
State = Data.define(:speed)
|
47
|
+
Started = Data.define(:speed)
|
48
|
+
Stopped = Data.define
|
49
|
+
|
50
|
+
decider = Decider.define do
|
51
|
+
initial_state State.new(speed: 0)
|
52
|
+
|
53
|
+
evolve Started do |state, event|
|
54
|
+
State.new(speed: event.speed)
|
55
|
+
end
|
56
|
+
|
57
|
+
evolve Stopped do |state, event|
|
58
|
+
State.new(speed: 0)
|
59
|
+
end
|
60
|
+
end
|
61
|
+
```
|
62
|
+
|
data/lib/decider/version.rb
CHANGED
data/lib/decider.rb
CHANGED
@@ -29,7 +29,7 @@ module Decider
|
|
29
29
|
end
|
30
30
|
|
31
31
|
class Module < ::Module
|
32
|
-
def initialize(initial_state:, deciders:,
|
32
|
+
def initialize(initial_state:, deciders:, evolutions:, terminal:)
|
33
33
|
define_method(:initial_state) do
|
34
34
|
initial_state
|
35
35
|
end
|
@@ -39,39 +39,43 @@ module Decider
|
|
39
39
|
end
|
40
40
|
|
41
41
|
define_method(:events) do
|
42
|
-
|
42
|
+
evolutions.keys
|
43
43
|
end
|
44
44
|
|
45
45
|
define_method(:decide!) do |command, state|
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
46
|
+
case deciders.find { |key, _| key === command }
|
47
|
+
in [_, handler]
|
48
|
+
handler.call(command, state)
|
49
|
+
else
|
50
|
+
raise ArgumentError, "Unknown command: #{command.inspect}"
|
51
|
+
end
|
51
52
|
end
|
52
53
|
|
53
54
|
define_method(:decide) do |command, state|
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
55
|
+
case deciders.find { |key, _| key === command }
|
56
|
+
in [_, handler]
|
57
|
+
handler.call(command, state)
|
58
|
+
else
|
59
|
+
[]
|
60
|
+
end
|
59
61
|
end
|
60
62
|
|
61
63
|
define_method(:evolve!) do |state, event|
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
64
|
+
case evolutions.find { |key, _| key === event }
|
65
|
+
in [_, handler]
|
66
|
+
handler.call(state, event)
|
67
|
+
else
|
68
|
+
raise ArgumentError, "Unknown event: #{event.inspect}"
|
69
|
+
end
|
67
70
|
end
|
68
71
|
|
69
72
|
define_method(:evolve) do |state, event|
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
73
|
+
case evolutions.find { |key, _| key === event }
|
74
|
+
in [_, handler]
|
75
|
+
handler.call(state, event)
|
76
|
+
else
|
77
|
+
state
|
78
|
+
end
|
75
79
|
end
|
76
80
|
|
77
81
|
define_method(:terminal?) do |state|
|
@@ -88,7 +92,7 @@ module Decider
|
|
88
92
|
def initialize
|
89
93
|
@initial_state = DEFAULT
|
90
94
|
@deciders = {}
|
91
|
-
@
|
95
|
+
@evolutions = {}
|
92
96
|
@terminal = ->(_state) { false }
|
93
97
|
end
|
94
98
|
|
@@ -97,12 +101,12 @@ module Decider
|
|
97
101
|
|
98
102
|
raise StateNotDefined if @initial_state == DEFAULT
|
99
103
|
|
100
|
-
decider =
|
104
|
+
decider = Class.new
|
101
105
|
|
102
106
|
@module = Module.new(
|
103
107
|
initial_state: @initial_state,
|
104
108
|
deciders: deciders,
|
105
|
-
|
109
|
+
evolutions: evolutions,
|
106
110
|
terminal: terminal
|
107
111
|
)
|
108
112
|
|
@@ -113,7 +117,7 @@ module Decider
|
|
113
117
|
|
114
118
|
private
|
115
119
|
|
116
|
-
attr_reader :deciders, :
|
120
|
+
attr_reader :deciders, :evolutions, :terminal
|
117
121
|
|
118
122
|
def initial_state(state)
|
119
123
|
raise StateAlreadyDefined if @initial_state != DEFAULT
|
@@ -126,7 +130,7 @@ module Decider
|
|
126
130
|
end
|
127
131
|
|
128
132
|
def evolve(event, &block)
|
129
|
-
|
133
|
+
evolutions[event] = block
|
130
134
|
end
|
131
135
|
|
132
136
|
def terminal?(&block)
|