delayer-deferred 1.1.1 → 2.0.0
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/README.md +77 -3
- data/delayer-deferred.gemspec +1 -0
- data/lib/delayer/deferred.rb +11 -10
- data/lib/delayer/deferred/chain.rb +10 -0
- data/lib/delayer/deferred/chain/await.rb +43 -0
- data/lib/delayer/deferred/chain/base.rb +35 -0
- data/lib/delayer/deferred/chain/next.rb +16 -0
- data/lib/delayer/deferred/chain/trap.rb +16 -0
- data/lib/delayer/deferred/deferred.rb +4 -72
- data/lib/delayer/deferred/deferredable.rb +8 -158
- data/lib/delayer/deferred/deferredable/awaitable.rb +27 -0
- data/lib/delayer/deferred/deferredable/chainable.rb +155 -0
- data/lib/delayer/deferred/deferredable/graph.rb +118 -0
- data/lib/delayer/deferred/deferredable/node_sequence.rb +158 -0
- data/lib/delayer/deferred/deferredable/trigger.rb +34 -0
- data/lib/delayer/deferred/enumerator.rb +5 -7
- data/lib/delayer/deferred/error.rb +9 -0
- data/lib/delayer/deferred/promise.rb +78 -0
- data/lib/delayer/deferred/request.rb +61 -0
- data/lib/delayer/deferred/response.rb +26 -0
- data/lib/delayer/deferred/thread.rb +29 -14
- data/lib/delayer/deferred/tools.rb +20 -10
- data/lib/delayer/deferred/version.rb +1 -1
- data/lib/delayer/deferred/worker.rb +112 -0
- data/test/deferred_test.rb +14 -0
- data/test/enumerable_test.rb +1 -1
- data/test/graph_test.rb +52 -0
- data/test/helper.rb +8 -3
- data/test/promise_test.rb +91 -0
- data/test/thread_test.rb +9 -5
- metadata +35 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 5fe3336ed51fed19dfd37766cf6b1144a6a8de45
|
4
|
+
data.tar.gz: ceb10cb5738de56ccd937ef6e8ee253ca6c0756e
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f7e52f1cf451cfc12e61d9712d55113e7d42a8f68b57459b7b9c55a9b04e93c6fad6a171a0de157f40583b5fac29f350ab1204513ddd100801da468baf47e87c
|
7
|
+
data.tar.gz: a72e6d3f75728f7b93296acc387207ec2aaa4e3ce809cd564bff82ef298934168b769af87d2ead3b22752bcd2ab29e6f7de0d15924b25aec83114e609fa143ed
|
data/README.md
CHANGED
@@ -1,7 +1,6 @@
|
|
1
1
|
# Delayer::Deferred
|
2
2
|
|
3
|
-
Delayer
|
4
|
-
jsdeferredでできること以外に、Thread、Enumeratorを拡張します。
|
3
|
+
Delayerの、ブロックを実行キューにキューイングする機能を利用し、エラー処理やasync/awaitのような機能をサポートするライブラリです。
|
5
4
|
|
6
5
|
## Installation
|
7
6
|
|
@@ -101,7 +100,7 @@ Error occured!
|
|
101
100
|
```
|
102
101
|
|
103
102
|
### Thread
|
104
|
-
Threadには、
|
103
|
+
Threadには、nextやtrapメソッドが実装されているので、Deferredのように扱うことができます。
|
105
104
|
|
106
105
|
```ruby
|
107
106
|
Delayer.default = Delayer.generate_class # Delayerの準備
|
@@ -117,6 +116,8 @@ Delayer.run
|
|
117
116
|
2
|
118
117
|
```
|
119
118
|
|
119
|
+
この場合、nextやtrapのブロックは、全て `Delayer.run` メソッドが実行された側のThreadで実行されます。
|
120
|
+
|
120
121
|
### Automatically Divide a Long Loop
|
121
122
|
`Enumerable#deach`, `Enumerator#deach`はeachの変種で、Delayerのexpireの値よりループに時間がかかったら一旦処理を中断して、続きを実行するDeferredを新たに作ります。
|
122
123
|
|
@@ -156,6 +157,79 @@ divided
|
|
156
157
|
|
157
158
|
また、このメソッドはDeferredを返すので、ループが終わった後に処理をしたり、エラーを受け取ったりできます。
|
158
159
|
|
160
|
+
### Pass to another Delayer
|
161
|
+
|
162
|
+
Deferredのコンテキストの中で `Deferred.pass` を呼ぶと、そこで一旦処理が中断し、キューの最後に並び直します。
|
163
|
+
他のDelayerが処理され終わると `Deferred.pass` から処理が戻ってきて、再度そこから実行が再開されます。
|
164
|
+
|
165
|
+
`Deferred.pass` は常に処理を中断するわけではなく、Delayerの時間制限を過ぎている場合にのみ処理をブレークします。
|
166
|
+
用途としては `Enumerator#deach` が使えないようなループの中で毎回呼び出して、長時間処理をブロックしないようにするといった用途が考えられます。
|
167
|
+
|
168
|
+
`Enumerator#deach` は `Deferred.pass` を用いて作られています。
|
169
|
+
|
170
|
+
### Combine Deferred
|
171
|
+
|
172
|
+
`Deferred.when` は、引数に2つ以上のDeferredを受け取り、新たなDeferredを一つ返します。
|
173
|
+
|
174
|
+
引数のDeferredすべてが正常に終了したら、戻り値のDeferredのnextブロックが呼ばれ、whenの引数の順番通りに戻り値が渡されます。
|
175
|
+
複数のDeferredがあって、それらすべてが終了するのを待ち合わせる時に使うと良いでしょう。
|
176
|
+
|
177
|
+
```ruby
|
178
|
+
web_a = Thread.new{ open("http://example.com/a.html") }
|
179
|
+
web_b = Thread.new{ open("http://example.com/b.html") }
|
180
|
+
web_c = Thread.new{ open("http://example.com/c.html") }
|
181
|
+
|
182
|
+
# 引数の順番は対応している
|
183
|
+
Deferred.when(web_a, web_b, web_c).next do |a, b, c|
|
184
|
+
...
|
185
|
+
end
|
186
|
+
|
187
|
+
# 配列を渡すことも出来る
|
188
|
+
Deferred.when([web_a, web_b, web_c]).next do |a, b, c|
|
189
|
+
...
|
190
|
+
end
|
191
|
+
|
192
|
+
```
|
193
|
+
|
194
|
+
引数のDeferredのうち、どれか一つでも失敗すると、直ちに `Deferred.when` の戻り値のtrapブロックが呼ばれます。trapの引数は、失敗したDeferredのそれです。
|
195
|
+
|
196
|
+
どれか一つでも失敗すると、他のDeferredが成功していたとしてもその結果は破棄されるということに気をつけてください。より細かく制御したい場合は、Async/Awaitを利用しましょう。
|
197
|
+
|
198
|
+
```ruby
|
199
|
+
divzero = Delayer::Deferred.new {
|
200
|
+
1 / 0
|
201
|
+
}
|
202
|
+
web_a = Thread.new{ open("http://example.com/a.html") }
|
203
|
+
|
204
|
+
Deferred.when(divzero, web_a).next{
|
205
|
+
puts 'success'
|
206
|
+
}.trap{|err|
|
207
|
+
p err
|
208
|
+
}
|
209
|
+
```
|
210
|
+
|
211
|
+
```
|
212
|
+
\#<ZeroDivisionError: divided by 0>
|
213
|
+
```
|
214
|
+
|
215
|
+
### Async/Await
|
216
|
+
|
217
|
+
Deferred#next や Deferred#trap のブロック内では、Deferredable#+@ が使えます。非同期な処理を同期処理のように書くことができます。
|
218
|
+
|
219
|
+
+@を呼び出すと、呼び出し元のDeferredの処理が一時停止し、+@のレシーバになっているDeferredableが完了した後に処理が再開されます。また、戻り値はレシーバのDeferredableのそれになります。
|
220
|
+
|
221
|
+
```
|
222
|
+
request = Thread.new{ open("http://mikutter.hachune.net/download/unstable.json").read }
|
223
|
+
Deferred.next{
|
224
|
+
puts "最新の不安定版mikutterのバージョンは"
|
225
|
+
response = JSON.parse(+request)
|
226
|
+
puts response.first["version_string"]
|
227
|
+
puts "です"
|
228
|
+
}
|
229
|
+
```
|
230
|
+
|
231
|
+
`+request` が呼ばれた時、リクエスト完了まで処理は一時止まりますが、他にDelayerキューにジョブが溜まっていたら、そちらが実行されます。この機能を使わない場合は、HTTPレスポンスを受け取るまでDelayerの他のジョブは停止してしまいます。
|
232
|
+
|
159
233
|
## Contributing
|
160
234
|
|
161
235
|
1. Fork it ( https://github.com/toshia/delayer-deferred/fork )
|
data/delayer-deferred.gemspec
CHANGED
@@ -25,6 +25,7 @@ Gem::Specification.new do |spec|
|
|
25
25
|
spec.add_development_dependency "bundler", "~> 1.7"
|
26
26
|
spec.add_development_dependency "rake", "~> 10.0"
|
27
27
|
spec.add_development_dependency "minitest", "~> 5.7"
|
28
|
+
spec.add_development_dependency "simplecov"
|
28
29
|
spec.add_development_dependency "ruby-prof"
|
29
30
|
spec.add_development_dependency 'guard'
|
30
31
|
spec.add_development_dependency 'guard-shell'
|
data/lib/delayer/deferred.rb
CHANGED
@@ -10,25 +10,26 @@ require "delayer/deferred/version"
|
|
10
10
|
|
11
11
|
module Delayer
|
12
12
|
module Deferred
|
13
|
-
extend Delayer::Deferred::Tools
|
14
|
-
|
15
13
|
class << self
|
16
14
|
#真ならデバッグ情報を集める
|
17
15
|
attr_accessor :debug
|
18
16
|
|
19
|
-
def
|
20
|
-
Delayer::Deferred::Deferred.
|
17
|
+
def method_missing(*rest, &block)
|
18
|
+
Delayer::Deferred::Deferred.__send__(*rest, &block)
|
19
|
+
end
|
21
20
|
end
|
22
21
|
end
|
23
22
|
|
24
23
|
module Extend
|
25
|
-
def
|
26
|
-
@
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
24
|
+
def Promise
|
25
|
+
@promise ||= begin
|
26
|
+
the_delayer = self
|
27
|
+
Class.new(::Delayer::Deferred::Promise) {
|
28
|
+
define_singleton_method(:delayer) {
|
29
|
+
the_delayer } } end
|
31
30
|
end
|
31
|
+
alias :Deferred :Promise
|
32
|
+
#deprecate :Deferred, "Promise", 2018, 03
|
32
33
|
end
|
33
34
|
end
|
34
35
|
|
@@ -0,0 +1,43 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
require "delayer/deferred/chain/base"
|
3
|
+
|
4
|
+
module Delayer::Deferred::Chain
|
5
|
+
class Await < Base
|
6
|
+
def initialize(worker:, deferred:)
|
7
|
+
super()
|
8
|
+
@worker, @awaiting_deferred = worker, deferred
|
9
|
+
deferred.add_awaited(self)
|
10
|
+
end
|
11
|
+
|
12
|
+
def activate(response)
|
13
|
+
change_sequence(:activate)
|
14
|
+
@worker.give_response(response, @awaiting_deferred)
|
15
|
+
# TODO: 即座にspoilさせてよさそう
|
16
|
+
ensure
|
17
|
+
change_sequence(:complete)
|
18
|
+
end
|
19
|
+
|
20
|
+
def graph_child(output:)
|
21
|
+
output << graph_mynode
|
22
|
+
if has_child?
|
23
|
+
@child.graph_child(output: output)
|
24
|
+
@awaiting_deferred.graph_child(output: output)
|
25
|
+
output << "#{__id__} -> #{@child.__id__}"
|
26
|
+
end
|
27
|
+
nil
|
28
|
+
end
|
29
|
+
|
30
|
+
def node_name
|
31
|
+
"Await"
|
32
|
+
end
|
33
|
+
|
34
|
+
def graph_shape
|
35
|
+
'circle'.freeze
|
36
|
+
end
|
37
|
+
|
38
|
+
def graph_mynode
|
39
|
+
label = "#{node_name}\n(#{sequence.name})"
|
40
|
+
"#{__id__} [shape=#{graph_shape},label=#{label.inspect}]"
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
require "delayer/deferred/deferredable/chainable"
|
3
|
+
require "delayer/deferred/deferredable/node_sequence"
|
4
|
+
|
5
|
+
module Delayer::Deferred::Chain
|
6
|
+
class Base
|
7
|
+
include Delayer::Deferred::Deferredable::NodeSequence
|
8
|
+
include Delayer::Deferred::Deferredable::Chainable
|
9
|
+
|
10
|
+
def initialize(&proc)
|
11
|
+
fail Error, "Delayer::Deferred::Chain can't create instance." if self.class == Delayer::Deferred::Chain::Base
|
12
|
+
@proc = proc
|
13
|
+
end
|
14
|
+
|
15
|
+
def activate(response)
|
16
|
+
change_sequence(:activate)
|
17
|
+
if evaluate?(response)
|
18
|
+
@proc.(response.value)
|
19
|
+
else
|
20
|
+
response
|
21
|
+
end
|
22
|
+
ensure
|
23
|
+
change_sequence(:complete)
|
24
|
+
end
|
25
|
+
|
26
|
+
def inspect
|
27
|
+
"#<#{self.class} seq:#{sequence.name} child:#{has_child?}>"
|
28
|
+
end
|
29
|
+
|
30
|
+
def node_name
|
31
|
+
@proc.source_location.join(':'.freeze)
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
@@ -1,78 +1,10 @@
|
|
1
1
|
# -*- coding: utf-8 -*-
|
2
|
+
require "delayer/deferred/promise"
|
3
|
+
require "delayer/deferred/chain"
|
2
4
|
require "delayer/deferred/deferredable"
|
3
|
-
require "delayer/deferred/
|
5
|
+
require "delayer/deferred/worker"
|
4
6
|
require "delayer/deferred/version"
|
5
7
|
|
6
8
|
module Delayer::Deferred
|
7
|
-
|
8
|
-
extend Delayer::Deferred::Tools
|
9
|
-
include Deferredable
|
10
|
-
|
11
|
-
def self.inherited(subclass)
|
12
|
-
subclass.extend(::Delayer::Deferred)
|
13
|
-
end
|
14
|
-
|
15
|
-
def self.Thread
|
16
|
-
@thread_class ||= gen_thread_class end
|
17
|
-
|
18
|
-
def self.gen_thread_class
|
19
|
-
the_delayer = delayer
|
20
|
-
Class.new(Thread) do
|
21
|
-
define_singleton_method(:delayer) do
|
22
|
-
the_delayer end end end
|
23
|
-
|
24
|
-
def self.delayer
|
25
|
-
::Delayer end
|
26
|
-
|
27
|
-
def self.new(*args)
|
28
|
-
deferred = super(*args)
|
29
|
-
if block_given?
|
30
|
-
deferred.next(&Proc.new)
|
31
|
-
else
|
32
|
-
deferred end
|
33
|
-
end
|
34
|
-
|
35
|
-
def initialize(follow = nil)
|
36
|
-
super()
|
37
|
-
@follow = follow
|
38
|
-
@backtrace = caller if ::Delayer::Deferred.debug end
|
39
|
-
|
40
|
-
alias :deferredable_cancel :cancel
|
41
|
-
def cancel
|
42
|
-
deferredable_cancel
|
43
|
-
@follow.cancel if @follow.is_a? Deferredable end
|
44
|
-
|
45
|
-
def inspect
|
46
|
-
if ::Delayer::Deferred.debug
|
47
|
-
sprintf("#<%s: %p %s follow:%p stat:%s value:%s>".freeze, self.class, object_id, @backtrace.find{|n|not n.include?("delayer/deferred".freeze)}, @follow ? @follow.object_id : 0, @next_call_stat.inspect, @next_call_value.inspect)
|
48
|
-
else
|
49
|
-
sprintf("#<%s: %p stat:%s value:%s>".freeze, self.class, object_id, @next_call_stat.inspect, @next_call_value.inspect)
|
50
|
-
end
|
51
|
-
end
|
52
|
-
|
53
|
-
def self.fiber(&block)
|
54
|
-
@_fiber ||= _gen_new_fiber
|
55
|
-
begin
|
56
|
-
result = @_fiber.resume(block)
|
57
|
-
rescue FiberError
|
58
|
-
@_fiber = _gen_new_fiber
|
59
|
-
result = @_fiber.resume(block)
|
60
|
-
end
|
61
|
-
if result.is_a?(Delayer::Deferred::ResultContainer)
|
62
|
-
result
|
63
|
-
else
|
64
|
-
_fiber = @_fiber
|
65
|
-
@_fiber = nil
|
66
|
-
return result, _fiber
|
67
|
-
end
|
68
|
-
end
|
69
|
-
|
70
|
-
def self._gen_new_fiber
|
71
|
-
Fiber.new do |b|
|
72
|
-
loop do
|
73
|
-
b = Fiber.yield(b.())
|
74
|
-
end
|
75
|
-
end
|
76
|
-
end
|
77
|
-
end
|
9
|
+
Deferred = Promise
|
78
10
|
end
|
@@ -1,162 +1,12 @@
|
|
1
1
|
# -*- coding: utf-8 -*-
|
2
2
|
require "delayer/deferred/version"
|
3
|
-
require "delayer/deferred/result_container"
|
4
|
-
|
5
|
-
# なんでもDeferred
|
6
|
-
module Delayer::Deferred::Deferredable
|
7
|
-
Callback = Struct.new(*%i<ok ng backtrace>)
|
8
|
-
CallbackDefaultOK = lambda{ |x| x }
|
9
|
-
CallbackDefaultNG = lambda{ |err| Delayer::Deferred.fail(err) }
|
10
|
-
|
11
|
-
# このDeferredが成功した場合の処理を追加する。
|
12
|
-
# 新しいDeferredのインスタンスを返す
|
13
|
-
def next(&proc)
|
14
|
-
_post(:ok, &proc) end
|
15
|
-
alias deferred next
|
16
|
-
|
17
|
-
# このDeferredが失敗した場合の処理を追加する。
|
18
|
-
# 新しいDeferredのインスタンスを返す
|
19
|
-
def trap(&proc)
|
20
|
-
_post(:ng, &proc) end
|
21
|
-
alias error trap
|
22
|
-
|
23
|
-
# Deferredを直ちに実行する
|
24
|
-
def call(value = nil)
|
25
|
-
_call(:ok, value) end
|
26
|
-
|
27
|
-
# Deferredを直ちに失敗させる
|
28
|
-
def fail(exception = nil)
|
29
|
-
_call(:ng, exception) end
|
30
|
-
|
31
|
-
# _self_ が終了して結果が出るまで呼び出し側のDeferredを停止し、 _self_ の結果を返す。
|
32
|
-
# 呼び出し側はDeferredブロック内でなければならないが、 _Deferred#next_ を使わずに
|
33
|
-
# 直接戻り値を得ることが出来る。
|
34
|
-
# _self_ が失敗した場合は、呼び出し側のDeferredの直近の _trap_ ブロックが呼ばれる。
|
35
|
-
def +@
|
36
|
-
interrupt = Fiber.yield(self)
|
37
|
-
if interrupt.ok?
|
38
|
-
interrupt.value
|
39
|
-
else
|
40
|
-
Delayer::Deferred.fail(interrupt.value)
|
41
|
-
end
|
42
|
-
end
|
43
|
-
|
44
|
-
# この一連のDeferredをこれ以上実行しない
|
45
|
-
def cancel
|
46
|
-
@callback = Callback.new(CallbackDefaultOK,
|
47
|
-
CallbackDefaultNG).freeze end
|
48
|
-
|
49
|
-
def callback
|
50
|
-
@callback ||= Callback.new(CallbackDefaultOK,
|
51
|
-
CallbackDefaultNG) end
|
52
|
-
|
53
|
-
# second 秒待って次を実行する
|
54
|
-
# ==== Args
|
55
|
-
# [second] 待つ秒数(second)
|
56
|
-
# ==== Return
|
57
|
-
# Deferred
|
58
|
-
def wait(second)
|
59
|
-
self.next{ Thread.new{ sleep(second) } } end
|
60
|
-
|
61
|
-
private
|
62
|
-
|
63
|
-
def delayer
|
64
|
-
self.class.delayer
|
65
|
-
end
|
66
|
-
|
67
|
-
def _call(stat = :ok, value = nil)
|
68
|
-
delayer.new do
|
69
|
-
result, fiber = delayer.Deferred.fiber do
|
70
|
-
begin
|
71
|
-
result = catch(:__deferredable_fail) do
|
72
|
-
Delayer::Deferred::ResultContainer.new(true, _execute(stat, value))
|
73
|
-
end
|
74
|
-
if result.is_a?(Delayer::Deferred::ResultContainer)
|
75
|
-
result
|
76
|
-
else
|
77
|
-
Delayer::Deferred::ResultContainer.new(false, result)
|
78
|
-
end
|
79
|
-
rescue Exception => exception
|
80
|
-
Delayer::Deferred::ResultContainer.new(false, exception)
|
81
|
-
end
|
82
|
-
end
|
83
|
-
#_wait_fiber(fiber, nil)
|
84
|
-
if fiber
|
85
|
-
_fiber_stopped(result){|i| _wait_fiber(fiber, i) }
|
86
|
-
else
|
87
|
-
_fiber_completed(result)
|
88
|
-
end
|
89
|
-
end
|
90
|
-
end
|
91
|
-
|
92
|
-
|
93
|
-
def _execute(stat, value)
|
94
|
-
callback[stat].call(value)
|
95
|
-
end
|
96
|
-
|
97
|
-
def _wait_fiber(fiber, resume_value)
|
98
|
-
result = fiber.resume(resume_value)
|
99
|
-
if result.is_a?(Delayer::Deferred::ResultContainer)
|
100
|
-
_fiber_completed(result)
|
101
|
-
else
|
102
|
-
_fiber_stopped(result){|i| _wait_fiber(fiber, i) }
|
103
|
-
end
|
104
|
-
end
|
105
|
-
|
106
|
-
# Deferredブロックが最後まで終わり、これ以上やることがない時に呼ばれる
|
107
|
-
def _fiber_completed(result)
|
108
|
-
result_value = result.value
|
109
|
-
if result.ok?
|
110
|
-
if result_value.is_a?(Delayer::Deferred::Deferredable)
|
111
|
-
result_value.next{|v|
|
112
|
-
_success_action(v)
|
113
|
-
}.trap{|v|
|
114
|
-
_fail_action(v)
|
115
|
-
}
|
116
|
-
else
|
117
|
-
_success_action(result_value)
|
118
|
-
end
|
119
|
-
else
|
120
|
-
_fail_action(result_value)
|
121
|
-
end
|
122
|
-
end
|
123
|
-
|
124
|
-
# Deferredable#@+によって停止され、 _defer_ の完了次第処理を再開する必要がある時に呼ばれる
|
125
|
-
def _fiber_stopped(defer, &cont)
|
126
|
-
defer.next{|v|
|
127
|
-
cont.(Delayer::Deferred::ResultContainer.new(true, v))
|
128
|
-
}.trap{|v|
|
129
|
-
cont.(Delayer::Deferred::ResultContainer.new(false, v))
|
130
|
-
}
|
131
|
-
end
|
132
|
-
|
133
|
-
def _post(kind, &proc)
|
134
|
-
@next = delayer.Deferred.new(self)
|
135
|
-
@next.callback[kind] = proc
|
136
|
-
if defined?(@next_call_stat) and defined?(@next_call_value)
|
137
|
-
@next.__send__({ok: :call, ng: :fail}[@next_call_stat], @next_call_value)
|
138
|
-
elsif defined?(@follow) and @follow.nil?
|
139
|
-
call end
|
140
|
-
@next end
|
141
|
-
|
142
|
-
def register_next_call(stat, value)
|
143
|
-
@next_call_stat, @next_call_value = stat, value
|
144
|
-
self end
|
145
|
-
|
146
|
-
def _success_action(obj)
|
147
|
-
if defined?(@next)
|
148
|
-
@next.call(obj)
|
149
|
-
else
|
150
|
-
register_next_call(:ok, obj)
|
151
|
-
end
|
152
|
-
end
|
153
|
-
|
154
|
-
def _fail_action(err_obj)
|
155
|
-
if defined?(@next)
|
156
|
-
@next.fail(err_obj)
|
157
|
-
else
|
158
|
-
register_next_call(:ng, err_obj)
|
159
|
-
end
|
160
|
-
end
|
161
3
|
|
4
|
+
module Delayer::Deferred
|
5
|
+
module Deferredable; end
|
162
6
|
end
|
7
|
+
|
8
|
+
require "delayer/deferred/deferredable/awaitable"
|
9
|
+
require "delayer/deferred/deferredable/chainable"
|
10
|
+
require "delayer/deferred/deferredable/graph"
|
11
|
+
require "delayer/deferred/deferredable/node_sequence"
|
12
|
+
require "delayer/deferred/deferredable/trigger"
|