simple-fifo 1.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 ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: af466537c7b9bfa49ef532d011a082d3584ba7800a205ad1e591cc44dd10768d
4
+ data.tar.gz: f3241744fc946f73b932e5c068501fadfcfa5b845832e6a63af89e962de0bc37
5
+ SHA512:
6
+ metadata.gz: ab15739f205f44920f54efbfad23dea5739c37e260e3af47c0657aac754abaa696dec3deae0d45ec6da902ed2c90fd58a6310348e84065a7e050871018957405
7
+ data.tar.gz: 9b5244a9b08903a61a8948bf1fc4db114cf686769e4d37107597ab1ab6c94d885ce779c6a142a66bc9961936250e00ab05ece26655a32f687f5e5abf3365339f
data/.gitignore ADDED
@@ -0,0 +1,3 @@
1
+ spec/data
2
+ .rvmrc
3
+ Gemfile.lock
data/.travis.yml ADDED
@@ -0,0 +1,9 @@
1
+ rvm:
2
+ - 1.9.3
3
+ - 2.0.0
4
+ - 2.1.5
5
+ - 2.2.1
6
+
7
+ before_install:
8
+ - sudo apt-get update
9
+ - sudo apt-get install ruby-dev
data/Gemfile ADDED
@@ -0,0 +1,10 @@
1
+ source :rubygems
2
+
3
+ group :test do
4
+ gem 'rspec'
5
+ gem 'rake'
6
+ end
7
+
8
+ group :development do
9
+ gem 'pry'
10
+ end
data/README.md ADDED
@@ -0,0 +1,124 @@
1
+ Forked from ruby-fifo: https://github.com/shurizzle/ruby-fifo
2
+
3
+ A small, simple library for using Fifos in Ruby. A Fifo is traditionally a Unix
4
+ idea that lets processes communicate by writing to and reading from a special
5
+ kind of file in the filesystem. More information on fifos can be found here:
6
+ [http://en.wikipedia.org/wiki/Named_pipe](http://en.wikipedia.org/wiki/Named_pipe).
7
+
8
+ # Installation
9
+
10
+ To install simple-fifo, execute the following command at your terminal:
11
+
12
+ $ gem install simple-fifo
13
+
14
+ Being sure not to include the dollar sign. The dollar sign is simply convention
15
+ for denoting a terminal command.
16
+
17
+ # Usage
18
+
19
+ To use a fifo, you need both a reader and a writer (the POSIX standard does not
20
+ define the behaviour from using the same file handle as both a reader and a
21
+ writer so this library does not allow it).
22
+
23
+ Here's some example code that will simply write to a fifo and read from it, all
24
+ in the same process:
25
+
26
+ ``` ruby
27
+ reader = Fifo.new('path/to/fifo', :r, :nowait)
28
+ writer = Fifo.new('path/to/fifo', :w, :nowait)
29
+
30
+ writer.puts "Hello, world!"
31
+ reader.gets
32
+ #=> "Hello, world!\n"
33
+ ```
34
+
35
+ Notice that we pass in `:r` and `:w` for the reader and writer respectively.
36
+ Also, we have this `:nowait` symbol in there. This tells the library that we
37
+ don't want to use "blocking" fifos.
38
+
39
+ ## Blocking vs Non-blocking
40
+
41
+ A blocking fifo will block the current thread of execution until the other end
42
+ is opened. For example, the following code will never finish executing:
43
+
44
+ ``` ruby
45
+ reader = Fifo.new('path/to/fifo', :r, :wait)
46
+ writer = Fifo.new('path/to/fifo', :w, :wait)
47
+ ```
48
+
49
+ The thread will be blocked after the first line and it will wait until the
50
+ writing end of the fifo is opened before allowing execution to continue. This
51
+ also works exactly the same way in reverse (if you opened the writer before the
52
+ reader).
53
+
54
+ The following code should work fine:
55
+
56
+ ``` ruby
57
+ fork do
58
+ reader = Fifo.new('path/to/fifo', :r, :wait)
59
+ reader.gets
60
+ #=> Eventually, this will return "Hello, fork!\n"
61
+ end
62
+
63
+ fork do
64
+ writer = Fifo.new('path/to/fifo', :w, :wait)
65
+ writer.puts "Hello, fork!"
66
+ end
67
+ ```
68
+
69
+ ### Non-blocking
70
+
71
+ Alternately, you can use non-blocking pipes. These pipes don't wait for the
72
+ other end to be open before doing there work. The following code will work just
73
+ fine all in the same process:
74
+
75
+ ``` ruby
76
+ writer = Fifo.new('path/to/fifo', :w, :nowait)
77
+ writer.puts "Testing"
78
+
79
+ reader = Fifo.new('path/to/fifo', :r, :nowait)
80
+ reader.gets
81
+ #=> "Testing\n"
82
+ ```
83
+
84
+ ### Defaults
85
+
86
+ Because of this, non-blocking is the default type of fifo that this library will
87
+ create.
88
+
89
+ ``` ruby
90
+ fifo = Fifo.new('path/to/fifo')
91
+ # This is a non-blocking reader by default
92
+ ```
93
+
94
+ ## Other methods for reading and writing
95
+
96
+ There are other forms of reading and writing that will be familiar to you if you
97
+ have used the Ruby File object:
98
+
99
+ ``` ruby
100
+ reader = Fifo.new('path/to/fifo', :r, :nowait)
101
+ writer = Fifo.new('path/to/fifo', :w, :nowait)
102
+
103
+ writer.puts "Two", "Lines"
104
+ reader.gets
105
+ #=> "Two\n"
106
+ reader.gets
107
+ #=> "Lines\n"
108
+
109
+ writer.print "12345"
110
+ # reader.gets would block forever here, no new line
111
+ reader.getc
112
+ #=> "1"
113
+ reader.read(1)
114
+ #=> "2"
115
+ reader.read(3)
116
+ #=> "345"
117
+
118
+ # reader.read(1)
119
+ #=> Blocks until something is written
120
+
121
+ writer.print "Same as puts\n"
122
+ reader.readline
123
+ #=> "Same as puts\n"
124
+ ```
data/Rakefile ADDED
@@ -0,0 +1,14 @@
1
+ require 'rspec/core/rake_task'
2
+
3
+ task :default => [:spec]
4
+
5
+ desc "Run all tests."
6
+ RSpec::Core::RakeTask.new(:spec)
7
+
8
+ desc "Opens up an irb session with the load path and library required."
9
+ task :console do
10
+ exec "irb -I lib/ -r ./lib/simple-fifo.rb"
11
+ end
12
+
13
+ desc "Alias for rake console."
14
+ task :c => [:console]
@@ -0,0 +1,13 @@
1
+ libdir = File.dirname(__FILE__)
2
+ $LOAD_PATH.unshift(libdir) unless $LOAD_PATH.include?(libdir)
3
+
4
+ require 'forwardable'
5
+
6
+ if RUBY_PLATFORM =~ /mswin/
7
+ require 'web32/pipe'
8
+ $POSIX = false
9
+ else
10
+ $POSIX = true
11
+ end
12
+
13
+ require 'simple-fifo/fifo'
@@ -0,0 +1,139 @@
1
+ class Fifo
2
+ # Module to allow delegation
3
+ include Forwardable
4
+
5
+ # Constructs a new Fifo. Can open either a read or write fifo in either
6
+ # blocking or non-blocking mode.
7
+ #
8
+ # Examples:
9
+ #
10
+ # # Non-blocking read Fifo (default)
11
+ # r = Fifo.new('path/to/fifo')
12
+ #
13
+ # # Blocking read Fifo
14
+ # r = Fifo.new('path/to/fifo', :r, :wait)
15
+ #
16
+ # # Non blocking write Fifo
17
+ # w = Fifo.new('path/to/fifo', :w, :nowait)
18
+ def initialize(file, perms = :r, mode = :nowait)
19
+ raise 'Unknown file permission. Must be either :r or :w.' unless [:r, :w].include?(perms)
20
+
21
+ unless [:wait, :nowait].include?(mode)
22
+ raise 'Unknown file mode. Must be either :wait or :nowait for blocking' \
23
+ ' or non-blocking respectively.'
24
+ end
25
+
26
+ if $POSIX
27
+ unless File.exist?(file)
28
+ File.mkfifo(file)
29
+ File.chmod(0o0666, file)
30
+ end
31
+
32
+ perms = perms.to_s + (mode == :wait ? '' : '+')
33
+ @pipe = open_pipe(file, perms)
34
+ else
35
+ include Win32
36
+
37
+ mode = mode == :wait ? Pipe::WAIT : Pipe::NOWAIT
38
+ @pipe = perms == :r ? Pipe.new_server(file, mode) : Pipe.new_client(file)
39
+ @pipe.connect if perms == :r
40
+ end
41
+
42
+ def_delegators :@pipe, :read, :write, :close, :to_io, :flush
43
+ end
44
+
45
+ # Prints the arguments passed in to the fifo. to_s is called on either
46
+ # argument passed in.
47
+ #
48
+ # Example:
49
+ #
50
+ # f = Fifo.new('path/to/fifo', :w)
51
+ # f.print "Hello!"
52
+ # f.print "Multiple", "Arguments"
53
+ # f.puts "!" # Need a puts because fifos are line buffered
54
+ #
55
+ # r = Fifo.new('path/to/fifo', :r)
56
+ # r.gets
57
+ # #=> "Hello!MultipleArugments!\n"
58
+ def print(*args)
59
+ args.each do |obj|
60
+ self.write obj.to_s
61
+ end
62
+
63
+ write $OUTPUT_RECORD_SEPARATOR
64
+ flush
65
+ end
66
+
67
+ # Works the same as Kernel::puts, writes a string or multiple strings to the
68
+ # Fifo and then appends a new line. In the case of multiple arguments, a new
69
+ # line is printed after each one.
70
+ #
71
+ # Examples:
72
+ #
73
+ # w = Fifo.new('path/to/fifo', :w)
74
+ # r = Fifo.new('path/to/fifo', :r)
75
+ #
76
+ # w.puts "1", "2", "3", "4"
77
+ #
78
+ # r.gets
79
+ # #=> "1\n"
80
+ #
81
+ # r.gets
82
+ # #=> "2\n"
83
+ #
84
+ # r.gets
85
+ # #=> "3\n"
86
+ #
87
+ # r.gets
88
+ # #=> "4\n"
89
+ def puts(*args)
90
+ args.each do |obj|
91
+ self.write "#{obj.to_s.sub(/\n$/, '')}\n"
92
+ flush
93
+ end
94
+ end
95
+
96
+ # Reads a single character
97
+ #
98
+ # Alias for read(1).
99
+ def getc
100
+ self.read(1)
101
+ end
102
+
103
+ # Works in the same way as gets does but uses the $_ global variable for
104
+ # reading in each character. There is no functional difference between this
105
+ # and gets.
106
+ def readline
107
+ str = ''
108
+ while ($_ = self.read(1)) != "\n"
109
+ str << $_
110
+ end
111
+ str << "\n"
112
+ end
113
+
114
+ # Reads from the Fifo until it encounters a new line. Will block the current
115
+ # thread of execution until it hits a new line. This includes when the fifo is
116
+ # empty and nothing is writing to it.
117
+ #
118
+ # Example:
119
+ #
120
+ # w = Fifo.new('path/to/fifo', :w)
121
+ # r = Fifo.new('path/to/fifo', :r)
122
+ #
123
+ # w.puts "Hello, world!"
124
+ # r.gets
125
+ # #=> "Hello, world!\n"
126
+ def gets
127
+ self.readline
128
+ end
129
+
130
+ private
131
+
132
+ def open_pipe(file, perms)
133
+ File.open(file, perms)
134
+ rescue Errno::EINTR
135
+ # We just want to open a file, so keep retrying.
136
+ # Inspired by golang's solution: https://github.com/golang/go/commit/50d0ee0c98ea21f818d2daa9bc21ef51861a2ef9
137
+ retry
138
+ end
139
+ end
@@ -0,0 +1,18 @@
1
+ require 'rubygems'
2
+
3
+ Gem::Specification.new { |s|
4
+ s.name = 'simple-fifo'
5
+ s.version = '1.0.0'
6
+ s.author = ['shura', 'jackorp']
7
+ s.email = 'jar.prokop@volny.cz'
8
+ s.homepage = 'http://github.com/jackorp/simple-fifo'
9
+ s.platform = Gem::Platform::RUBY
10
+ s.required_ruby_version = '>= 1.9.2'
11
+ s.summary = 'A cross-platform library to use named pipe'
12
+ s.description = 'A FIFO library making I/O operations on FIFO files simple.'
13
+ s.files = Dir.chdir(File.expand_path('..', __FILE__)) do
14
+ `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
15
+ end
16
+ s.require_path = 'lib'
17
+ s.has_rdoc = true
18
+ }
metadata ADDED
@@ -0,0 +1,50 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: simple-fifo
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: ruby
6
+ authors:
7
+ - shura
8
+ - jackorp
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2021-06-13 00:00:00.000000000 Z
13
+ dependencies: []
14
+ description: A FIFO library making I/O operations on FIFO files simple.
15
+ email: jar.prokop@volny.cz
16
+ executables: []
17
+ extensions: []
18
+ extra_rdoc_files: []
19
+ files:
20
+ - ".gitignore"
21
+ - ".travis.yml"
22
+ - Gemfile
23
+ - README.md
24
+ - Rakefile
25
+ - lib/simple-fifo.rb
26
+ - lib/simple-fifo/fifo.rb
27
+ - simple-fifo.gemspec
28
+ homepage: http://github.com/jackorp/simple-fifo
29
+ licenses: []
30
+ metadata: {}
31
+ post_install_message:
32
+ rdoc_options: []
33
+ require_paths:
34
+ - lib
35
+ required_ruby_version: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - ">="
38
+ - !ruby/object:Gem::Version
39
+ version: 1.9.2
40
+ required_rubygems_version: !ruby/object:Gem::Requirement
41
+ requirements:
42
+ - - ">="
43
+ - !ruby/object:Gem::Version
44
+ version: '0'
45
+ requirements: []
46
+ rubygems_version: 3.2.15
47
+ signing_key:
48
+ specification_version: 4
49
+ summary: A cross-platform library to use named pipe
50
+ test_files: []