tent 0.0.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.
Files changed (3) hide show
  1. checksums.yaml +7 -0
  2. data/lib/tent.rb +86 -0
  3. metadata +72 -0
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 17beb0fbd92d9a1a66c936bdcfccf5bd3ea0f3a3
4
+ data.tar.gz: 61916d558c1534948c0dd59766b77b0d0b2eeaf5
5
+ SHA512:
6
+ metadata.gz: c98d8e56830c23af52be5c34fda1e265ec75030d61211c5f64af15659b521b03b6fcfe98ba27162f193104c1588b7bbad9909e7aa0e47d44cbf20bb6171cc084
7
+ data.tar.gz: 0451940ea06ef1f365cf16b88ee757b6576a3b4121eeaa01179b05cbdc451bc9d05e4d09893dac558047d1fcac768624ebefcb520f65ff03be13c01b65564cdd
@@ -0,0 +1,86 @@
1
+ require 'monitor'
2
+
3
+ # Provides a way of deferring method calls to
4
+ # an underlying object.
5
+ class Tent
6
+ include MonitorMixin
7
+
8
+ # Yields a `Tent` over the given `underlying`.
9
+ # By default, commits to the underlying when
10
+ # the block closes.
11
+ def self.cover(underlying, auto_commit = true, &block)
12
+ new(underlying).tap do |instance|
13
+ yield instance
14
+ instance.commit! if auto_commit
15
+ end
16
+ end
17
+
18
+ def initialize(underlying)
19
+ # Maintain a reference to the underlying:
20
+ @underlying = underlying
21
+ # Collect calls for the underlying:
22
+ @buffer = []
23
+ # Allow monitor mixin to initialise:
24
+ super()
25
+ end
26
+
27
+ # Provide access to the underlying object.
28
+ def direct
29
+ @underlying
30
+ end
31
+
32
+ # Clears the buffer. Optionally, only clears
33
+ # from the buffer.
34
+ def discard!(*filters)
35
+ process_buffer(false, filters)
36
+ end
37
+
38
+ # Commits the buffered calls to the underlying.
39
+ def commit!(*filters)
40
+ process_buffer(true, filters)
41
+ end
42
+
43
+ private
44
+
45
+ # Wrap calls to the underlying.
46
+ class BufferedCall
47
+ attr_reader :name, :args, :block
48
+
49
+ def initialize(name, *args, &block)
50
+ @name = name
51
+ @args = args
52
+ @block = block
53
+ end
54
+
55
+ def apply_to(target)
56
+ block ? target.send(name, *args, &block) : target.send(name, *args)
57
+ end
58
+
59
+ def matched_by?(filters)
60
+ 0 == filters.length || filters.include?(name)
61
+ end
62
+ end
63
+
64
+ # Clear from the buffer elements matching any
65
+ # of the `filters`. Will commit those elements
66
+ # to the underlying if `commit` is true.
67
+ def process_buffer(commit, filters)
68
+ synchronize do
69
+ @buffer.reject! do |call|
70
+ if call.matched_by?(filters)
71
+ call.apply_to(direct) if commit
72
+ true # Remove from buffer
73
+ end
74
+ end
75
+ end
76
+ end
77
+
78
+ def method_missing(method, *args, &block)
79
+ return super unless direct.respond_to?(method)
80
+
81
+ synchronize do
82
+ @buffer << BufferedCall.new(method, *args, &block)
83
+ self # Make buffering chainable.
84
+ end
85
+ end
86
+ end
metadata ADDED
@@ -0,0 +1,72 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: tent
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Josh Pencheon
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-09-14 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: minitest
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: 5.4.0
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: 5.4.0
27
+ - !ruby/object:Gem::Dependency
28
+ name: rake
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ description: Apply or forget interaction with a wrapped object
42
+ email:
43
+ executables: []
44
+ extensions: []
45
+ extra_rdoc_files: []
46
+ files:
47
+ - lib/tent.rb
48
+ homepage: http://rubygems.org/gems/tent
49
+ licenses:
50
+ - MIT
51
+ metadata: {}
52
+ post_install_message:
53
+ rdoc_options: []
54
+ require_paths:
55
+ - lib
56
+ required_ruby_version: !ruby/object:Gem::Requirement
57
+ requirements:
58
+ - - ">="
59
+ - !ruby/object:Gem::Version
60
+ version: '0'
61
+ required_rubygems_version: !ruby/object:Gem::Requirement
62
+ requirements:
63
+ - - ">="
64
+ - !ruby/object:Gem::Version
65
+ version: '0'
66
+ requirements: []
67
+ rubyforge_project:
68
+ rubygems_version: 2.2.2
69
+ signing_key:
70
+ specification_version: 4
71
+ summary: Conditional object wrapping
72
+ test_files: []