deferral 0.1.1 → 0.1.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.
- checksums.yaml +4 -4
- data/lib/deferral.rb +11 -4
- data/lib/deferral/deferred.rb +37 -0
- data/lib/deferral/stack_frame.rb +5 -8
- data/lib/deferral/version.rb +1 -1
- metadata +2 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: c29e4800b21774bc07464b24ccf6b55567e246d172078226c4efb75904a73d6d
|
4
|
+
data.tar.gz: 37e3137b7fd15b5020c8832ec9dd8c116aec606ae706725f801b7e5c1e84199a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: faadf44111eadf4ad96aeee801674e28ae5326fa493635e184e5189d353a56bf6653d3fd64faba72c9612ddbf17131c59a95e60dacf8dec9733440beae4f91a5
|
7
|
+
data.tar.gz: 7b259425ec31357c87c28910909ef0981ee275361728222f4effbd73787f88dbd023cc3b417ba291ec4368e2360e480f27562893181a1fe9a2bf6b48b89ec7de
|
data/lib/deferral.rb
CHANGED
@@ -23,32 +23,39 @@ module Deferral
|
|
23
23
|
|
24
24
|
stack = store[:stack] = [StackFrame.new(:root)] # root stack frame as first "caller" position of this method
|
25
25
|
first_return = true
|
26
|
+
stack_under_defer = false
|
26
27
|
|
27
28
|
trace = TracePoint.new(:call, :return, :b_call, :b_return) do |tp|
|
28
|
-
if tp.event == :return &&
|
29
|
+
if first_return && tp.event == :return && tp.defined_class == Deferral::Mixin && tp.method_id == :defer
|
29
30
|
first_return = false
|
30
31
|
next
|
31
32
|
end
|
32
33
|
|
33
34
|
case tp.event
|
34
35
|
when :call, :b_call
|
36
|
+
next if stack_under_defer
|
37
|
+
|
35
38
|
if tp.defined_class == Deferral::Mixin && tp.method_id == :defer
|
36
|
-
|
39
|
+
stack_under_defer = true
|
37
40
|
next
|
38
41
|
end
|
39
42
|
|
40
43
|
stack << StackFrame.new(tp.event)
|
44
|
+
|
41
45
|
when :return, :b_return
|
42
|
-
if tp.defined_class == Deferral::Mixin && tp.method_id == :defer
|
43
|
-
|
46
|
+
if stack_under_defer && tp.defined_class == Deferral::Mixin && tp.method_id == :defer
|
47
|
+
stack_under_defer = false
|
44
48
|
next
|
45
49
|
end
|
46
50
|
|
51
|
+
next if stack_under_defer
|
52
|
+
|
47
53
|
frame = stack.pop
|
48
54
|
frame.release!
|
49
55
|
if frame.root?
|
50
56
|
trace.disable
|
51
57
|
end
|
58
|
+
|
52
59
|
else
|
53
60
|
raise "unexpected TracePoint event:#{tp.event}"
|
54
61
|
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
module Deferral
|
2
|
+
class Deferred
|
3
|
+
def self.get_local_variables(block)
|
4
|
+
vars = {}
|
5
|
+
block.binding.local_variables.each do |name|
|
6
|
+
vars[name] = block.binding.local_variable_get(name)
|
7
|
+
end
|
8
|
+
vars
|
9
|
+
end
|
10
|
+
|
11
|
+
def self.set_local_variables(block, vars)
|
12
|
+
vars.each_pair do |name, val|
|
13
|
+
block.binding.local_variable_set(name, val)
|
14
|
+
end
|
15
|
+
nil
|
16
|
+
end
|
17
|
+
|
18
|
+
def initialize(block)
|
19
|
+
@block = block
|
20
|
+
@local_variables = Deferred.get_local_variables(block)
|
21
|
+
end
|
22
|
+
|
23
|
+
def call
|
24
|
+
current_vars = Deferred.get_local_variables(@block)
|
25
|
+
begin
|
26
|
+
Deferred.set_local_variables(@block, @local_variables)
|
27
|
+
@block.call
|
28
|
+
rescue Exception
|
29
|
+
# ignore all exceptions ...
|
30
|
+
# no way to add "suppressed" exceptions to the exception already thrown
|
31
|
+
ensure
|
32
|
+
Deferred.set_local_variables(@block, current_vars)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
data/lib/deferral/stack_frame.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
require_relative "./deferred"
|
2
|
+
|
1
3
|
module Deferral
|
2
4
|
class StackFrame
|
3
5
|
attr_reader :type, :id
|
@@ -12,18 +14,13 @@ module Deferral
|
|
12
14
|
end
|
13
15
|
|
14
16
|
def add(release)
|
15
|
-
@releases << release
|
17
|
+
@releases << Deferred.new(release)
|
16
18
|
end
|
17
19
|
|
18
20
|
def release!
|
19
21
|
return if @releases.empty?
|
20
|
-
@releases.reverse.each do |
|
21
|
-
|
22
|
-
r.call
|
23
|
-
rescue Exception
|
24
|
-
# ignore all exceptions ...
|
25
|
-
# no way to add "suppressed" exceptions to the exception already thrown
|
26
|
-
end
|
22
|
+
@releases.reverse.each do |d|
|
23
|
+
d.call
|
27
24
|
end
|
28
25
|
nil
|
29
26
|
end
|
data/lib/deferral/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: deferral
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- TAGOMORI Satoshi
|
@@ -66,6 +66,7 @@ files:
|
|
66
66
|
- Rakefile
|
67
67
|
- deferral.gemspec
|
68
68
|
- lib/deferral.rb
|
69
|
+
- lib/deferral/deferred.rb
|
69
70
|
- lib/deferral/kernel_ext.rb
|
70
71
|
- lib/deferral/stack_frame.rb
|
71
72
|
- lib/deferral/toplevel.rb
|