@@ -15,6 +15,8 @@ class IO
1515 class Stapled
1616 # If `#sync_close?` is `true`, closing this `IO` will close the underlying `IO`s.
1717 attr_accessor :sync_close
18+ attr_reader :reader
19+ attr_reader :writer
1820
1921 # Returns `true` if this `IO` is closed.
2022 #
@@ -23,6 +25,15 @@ class Stapled
2325
2426 @closed = false
2527
28+ WRITER_DELEGATE = %w[
29+ <<
30+ ] . freeze
31+
32+ READER_DELEGATE = %w[
33+ eof
34+ eof?
35+ ] . freeze
36+
2637 alias_method :sync_close? , :sync_close
2738 alias_method :closed? , :closed
2839
@@ -33,53 +44,30 @@ def initialize(reader, writer, sync_close: false)
3344 @sync_close = sync_close
3445 end
3546
36- def read ( ...)
37- check_open
38-
39- @reader . read ( ...)
40- end
41-
42- def readlines ( ...)
43- check_open
44-
45- @reader . readlines ( ...)
46- end
47-
48- def each_line ( ...)
49- check_open
50-
51- @reader . each_line ( ...)
47+ def method_missing ( name , *args , &block )
48+ if write_methods? ( name . to_s )
49+ check_open
50+ @writer . send ( name , *args , &block )
51+ elsif read_methods? ( name . to_s )
52+ check_open
53+ @reader . send ( name , *args , &block )
54+ else
55+ super
56+ end
5257 end
5358
54- # Gets a string from `reader`.
55- def gets ( ...)
56- check_open
57-
58- @reader . gets ( ...)
59+ def respond_to_missing? ( name , include_private = false )
60+ super || write_methods? ( name . to_s ) || read_methods? ( name . to_s )
5961 end
6062
61- def puts ( ...)
62- check_open
63-
64- @writer . puts ( ...)
63+ def write_methods? ( name )
64+ name . include? ( "put" ) || name . include? ( "prin" ) ||
65+ name . include? ( "write" ) || WRITER_DELEGATE . include? ( name )
6566 end
6667
67- def print ( ...)
68- check_open
69-
70- @writer . print ( ...)
71- end
72-
73- def printf ( ...)
74- check_open
75-
76- @writer . print ( ...)
77- end
78-
79- def write ( ...)
80- check_open
81-
82- @writer . write ( ...)
68+ def read_methods? ( name )
69+ name . include? ( "get" ) || name . include? ( "read" ) ||
70+ name . include? ( "each" ) || READER_DELEGATE . include? ( name )
8371 end
8472
8573 # Flushes `writer`.
@@ -91,6 +79,14 @@ def flush
9179 self
9280 end
9381
82+ def close_write
83+ @writer . close
84+ end
85+
86+ def close_read
87+ @reader . close
88+ end
89+
9490 # Closes this `IO`.
9591 #
9692 # If `sync_close?` is `true`, it will also close the underlying `IO`s.
@@ -105,14 +101,6 @@ def close
105101 end
106102 end
107103
108- def close_write
109- @writer . close
110- end
111-
112- def close_read
113- @reader . close
114- end
115-
116104 protected def check_open
117105 raise IOError . new ( "Closed stream" ) if closed?
118106 end
0 commit comments