em-fs 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.
data/.gitignore ADDED
@@ -0,0 +1,18 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
18
+ spec/data
data/.rspec ADDED
@@ -0,0 +1,2 @@
1
+ --color
2
+ --format progress
data/.rvmrc ADDED
@@ -0,0 +1 @@
1
+ rvm use --create --install 1.9.3@em-fs
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in em_file_utils.gemspec
4
+ gemspec
data/Guardfile ADDED
@@ -0,0 +1,19 @@
1
+ # A sample Guardfile
2
+ # More info at https://github.com/guard/guard#readme
3
+
4
+ guard 'rspec', :version => 2 do
5
+ watch(%r{^spec/.+_spec\.rb$})
6
+ watch(%r{^lib/(.+)\.rb$}) { |m| "spec/lib/#{m[1]}_spec.rb" }
7
+ watch('spec/spec_helper.rb') { "spec" }
8
+
9
+ # Rails example
10
+ watch(%r{^app/(.+)\.rb$}) { |m| "spec/#{m[1]}_spec.rb" }
11
+ watch(%r{^app/(.*)(\.erb|\.haml)$}) { |m| "spec/#{m[1]}#{m[2]}_spec.rb" }
12
+ watch(%r{^app/controllers/(.+)_(controller)\.rb$}) { |m| ["spec/routing/#{m[1]}_routing_spec.rb", "spec/#{m[2]}s/#{m[1]}_#{m[2]}_spec.rb", "spec/acceptance/#{m[1]}_spec.rb"] }
13
+ watch(%r{^spec/support/(.+)\.rb$}) { "spec" }
14
+ watch('config/routes.rb') { "spec/routing" }
15
+ watch('app/controllers/application_controller.rb') { "spec/controllers" }
16
+ # Capybara request specs
17
+ watch(%r{^app/views/(.+)/.*\.(erb|haml)$}) { |m| "spec/requests/#{m[1]}_spec.rb" }
18
+ end
19
+
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2012 Arthur Leonard Andersen
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,75 @@
1
+ # EM::FS
2
+
3
+ `EM::FS` provides a simple interface to gain simple filesystem access
4
+ in eventmachine via `EM::SystemCommand`.
5
+
6
+ `EM::FileUtils` attempts to mimic the behavoir of the filesystem API
7
+ of the Ruby stdlib. In the background it invokes linux/unix system
8
+ commands - like `rsync`, `mkdir` etc. - via the `em-systemcommand`
9
+ gem.
10
+
11
+ Furthermore `EM::Dir` and `EM::File` provide abstractions to crawl
12
+ directory structures via `find` command without blocking the reactor.
13
+
14
+ ## Installation
15
+
16
+ Add this line to your application's Gemfile:
17
+
18
+ gem 'em-fs'
19
+
20
+ And then execute:
21
+
22
+ $ bundle
23
+
24
+ Or install it yourself as:
25
+
26
+ $ gem install em-fs
27
+
28
+ ## Usage
29
+
30
+ ### `EM::FS` using `rsync` and `find`
31
+
32
+ To invoke bare commands you can either use `EM::SystemCommand`
33
+ directly or the methods `EM::FS.rsync` and `EM::FS.find`.
34
+
35
+ ### `EM::FileUtils` for simple filesystem operations
36
+
37
+ The `FileUtils` methods from the Ruby Standard Library may block the
38
+ eventmachine reactor. That´s why `em-fs` uses `EM::SystemCommand` to
39
+ provide a similar non-blocking feature set.
40
+
41
+ EM.run do
42
+ EM::FileUtils.cp 'some_file', 'some_copy' do |on|
43
+ on.exit do |status|
44
+ puts 'Copied!'
45
+ end
46
+ end
47
+ end
48
+
49
+ For a full list of methods, have a look at the documentation.
50
+
51
+ ### Abstraction via `EM::Dir` and `EM::File`
52
+
53
+ `EM::Dir[]` returns a `EM::Dir::Glob` object, containing the
54
+ information for the `find` command. On this object you can invoke
55
+ multiple methods to see the resulting filesystem objects:
56
+
57
+ EM::Dir['./**/*.*'].each do |stat|
58
+ puts "Some stat: #{stat.inspect}"
59
+ end
60
+
61
+ EM::Dir['./**/*.lisp'].each_entry do |entry|
62
+ puts "Some entry: #{entry}"
63
+ end
64
+
65
+ EM::Dir['./**/*.rb'].each_path do |path|
66
+ puts "Some path: #{path}"
67
+ end
68
+
69
+ ## Contributing
70
+
71
+ 1. Fork it
72
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
73
+ 3. Commit your changes (`git commit -am 'Added some feature'`)
74
+ 4. Push to the branch (`git push origin my-new-feature`)
75
+ 5. Create new Pull Request
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ #!/usr/bin/env rake
2
+ require "bundler/gem_tasks"
data/em-fs.gemspec ADDED
@@ -0,0 +1,26 @@
1
+ # -*- encoding: utf-8 -*-
2
+ require File.expand_path('../lib/em-fs/version', __FILE__)
3
+
4
+ Gem::Specification.new do |gem|
5
+ gem.authors = ["Arthur Leonard Andersen"]
6
+ gem.email = ["leoc.git@gmail.com"]
7
+ gem.description = %q{`em-fs` provides libraries to access file system commands through an API similar to the Ruby file API for eventmachine.}
8
+ gem.summary = %q{Invoke filesystem calls without blocking.}
9
+ gem.homepage = "http://github.com/leoc/em-fs"
10
+
11
+ gem.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
12
+ gem.files = `git ls-files`.split("\n")
13
+ gem.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
14
+ gem.name = "em-fs"
15
+ gem.require_paths = ["lib"]
16
+ gem.version = EventMachine::FS::VERSION
17
+
18
+ gem.add_development_dependency 'rake'
19
+ gem.add_development_dependency 'rspec'
20
+ gem.add_development_dependency 'guard'
21
+ gem.add_development_dependency 'guard-rspec'
22
+
23
+ gem.add_dependency 'eventmachine'
24
+ gem.add_dependency 'em-systemcommand'
25
+
26
+ end
@@ -0,0 +1,15 @@
1
+ class Hash
2
+ def extractable_options?
3
+ instance_of?(Hash)
4
+ end
5
+ end
6
+
7
+ class Array
8
+ def extract_options!
9
+ if last.is_a?(Hash) && last.extractable_options?
10
+ pop
11
+ else
12
+ {}
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,7 @@
1
+ module EventMachine
2
+ class Dir
3
+ class Glob
4
+
5
+ end
6
+ end
7
+ end
data/lib/em-fs/dir.rb ADDED
@@ -0,0 +1,14 @@
1
+ require 'em-fs/dir/glob'
2
+
3
+ module EventMachine
4
+ class Dir
5
+ class << self
6
+
7
+ def glob pattern
8
+ EM::Dir::Glob.new pattern
9
+ end
10
+ alias :[] :glob
11
+
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,200 @@
1
+ module EventMachine
2
+ class File
3
+ class Stat
4
+
5
+ STAT_REGEX = /(\d+) (\d+) (\d+) (\d+) (\h+) '([\w\/ ]+)' (\d+) (\d+) (\d+) '(.+)' '(.+)' (\d+) (\d+) (\h+) (\h+) (\d+) (\d+) (\d+) (\d+) (\d+)/.freeze
6
+ STAT_FORMAT = "%a %b %B %d %f '%F' %g %h %i '%m' '%n' %o %s %t %T %u %W %X %Y %Z"
7
+
8
+ # Types
9
+ S_IFBLK = 0b00000001 # block device
10
+ S_IFCHR = 0b00000010 # character device
11
+ S_IFDIR = 0b00000100 # directory
12
+ S_IFIFO = 0b00001000 # FIFO/pipe
13
+ S_IFLNK = 0b00010000 # symlink
14
+ S_IFREG = 0b00100000 # regular file
15
+ S_IFSOCK = 0b01000000 # socket
16
+ S_UNKNOWN = 0b10000000 # unknown
17
+
18
+ # Mode Flags
19
+ S_IRUSR = 0b100000000
20
+ S_IWUSR = 0b010000000
21
+ S_IXUSR = 0b001000000
22
+ S_IRGRP = 0b000100000
23
+ S_IWGRP = 0b000010000
24
+ S_IXGRP = 0b000001000
25
+ S_IROTH = 0b000000100
26
+ S_IWOTH = 0b000000010
27
+ S_IXOTH = 0b000000001
28
+
29
+ class << self
30
+
31
+ ##
32
+ # Parses a given string for file stat information.
33
+ #
34
+ # @param [String] string The String to be parsed.
35
+ # @return [EM::File::Stat] The file stat object.
36
+ def parse str
37
+ if m = str.match(STAT_REGEX)
38
+ ftype = case m[6]
39
+ when 'block device' then S_IFBLK
40
+ when 'character device' then S_IFCHR
41
+ when 'directory' then S_IFDIR
42
+ when 'FIFO/pipe' then S_IFIFO
43
+ when 'symlink' then S_IFLNK
44
+ when 'regular file' then S_IFREG
45
+ when 'socket' then S_IFSOCK
46
+ else
47
+ S_UNKNOWN
48
+ end
49
+ EM::File::Stat.new path: m[11],
50
+ mountpoint: m[10],
51
+ atime: Time.at(Integer(m[18], 10)),
52
+ blksize: Integer(m[3], 10),
53
+ blocks: Integer(m[2], 10),
54
+ ctime: Time.at(Integer(m[20], 10)),
55
+ dev: Integer(m[4], 10),
56
+ dev_major: Integer(m[14], 8),
57
+ dev_minor: Integer(m[15], 8),
58
+ ftype: ftype,
59
+ gid: Integer(m[7], 10),
60
+ ino: Integer(m[9], 10),
61
+ mode: Integer(m[1], 8),
62
+ mtime: Time.at(Integer(m[19], 10)),
63
+ nlink: Integer(m[8], 10),
64
+ size: Integer(m[13], 10),
65
+ uid: Integer(m[16], 10)
66
+ else
67
+ raise "Unable to parse stat string: #{str}"
68
+ end
69
+ end
70
+ end
71
+
72
+ attr_reader :path, :mountpoint, :atime, :blksize, :blocks, :ctime,
73
+ :dev, :dev_major, :dev_minor, :ftype, :gid, :ino, :mtime,
74
+ :nlink, :size, :uid
75
+
76
+ def initialize val = {}
77
+ @path = val[:path]
78
+ @mountpoint = val[:mountpoint]
79
+ @atime = val[:atime]
80
+ @blksize = val[:blksize]
81
+ @blocks = val[:blocks]
82
+ @ctime = val[:ctime]
83
+ @dev = val[:dev]
84
+ @dev_major = val[:dev_major]
85
+ @dev_minor = val[:dev_minor]
86
+ @ftype = val[:ftype]
87
+ @gid = val[:gid]
88
+ @ino = val[:ino]
89
+ @mode = val[:mode]
90
+ @mtime = val[:mtime]
91
+ @nlink = val[:nlink]
92
+ @size = val[:size]
93
+ @uid = val[:uid]
94
+ end
95
+
96
+ def blockdev?
97
+ ftype^S_IFBLK == 0
98
+ end
99
+
100
+ def chardev?
101
+ ftype^S_IFCHR == 0
102
+ end
103
+
104
+ def directory?
105
+ ftype^S_IFDIR == 0
106
+ end
107
+
108
+ def executable?
109
+ return true if Process::UID.rid == 0
110
+ return @mode & S_IXUSR != 0 if rowned?
111
+ return @mode & S_IXGRP != 0 if rgrpowned?
112
+ @mode & S_IXOTH != 0
113
+ end
114
+
115
+ def executable_real?
116
+ return true if Process::UID.rid == 0
117
+ return @mode & S_IXUSR != 0 if rowned?
118
+ return @mode & S_IXGRP != 0 if rgrpowned?
119
+ @mode & S_IXOTH != 0
120
+ end
121
+
122
+ def file?
123
+ ftype^S_IFREG == 0
124
+ end
125
+
126
+ def grpowned?
127
+ gid == Process::GID.eid
128
+ end
129
+
130
+ def rgrpowned?
131
+ gid == Process::GID.rid
132
+ end
133
+
134
+ def mode
135
+ @mode.to_s(8)
136
+ end
137
+
138
+ def owned?
139
+ uid == Process::UID.eid
140
+ end
141
+
142
+ def rowned?
143
+ uid == Process::UID.rid
144
+ end
145
+
146
+ def pipe?
147
+ ftype^S_IFIFO == 0
148
+ end
149
+
150
+ def readable?
151
+ return true if Process::UID.eid == 0
152
+ return @mode & S_IRUSR != 0 if owned?
153
+ return @mode & S_IRGRP != 0 if grpowned?
154
+ @mode & S_IROTH != 0
155
+ end
156
+
157
+ def readable_real?
158
+ return true if Process::UID.rid == 0
159
+ return @mode & S_IRUSR != 0 if rowned?
160
+ return @mode & S_IRGRP != 0 if rgrpowned?
161
+ @mode & S_IROTH != 0
162
+ end
163
+
164
+ def socket?
165
+ ftype^S_IFSOCK == 0
166
+ end
167
+
168
+ def symlink?
169
+ ftype^S_IFLNK == 0
170
+ end
171
+
172
+ def world_readable?
173
+ @mode if @mode & S_IROTH == S_IROTH
174
+ end
175
+
176
+ def world_writable?
177
+ @mode if @mode & S_IWOTH == S_IWOTH
178
+ end
179
+
180
+ def writable?
181
+ return true if Process::UID.rid == 0
182
+ return @mode & S_IWUSR != 0 if owned?
183
+ return @mode & S_IWGRP != 0 if grpowned?
184
+ @mode & S_IWOTH != 0
185
+ end
186
+
187
+ def writable_real?
188
+ return true if Process::UID.rid == 0
189
+ return @mode & S_IWUSR != 0 if rowned?
190
+ return @mode & S_IWGRP != 0 if rgrpowned?
191
+ @mode & S_IWOTH != 0
192
+ end
193
+
194
+ def zero?
195
+ @size == 0
196
+ end
197
+
198
+ end
199
+ end
200
+ end
data/lib/em-fs/file.rb ADDED
@@ -0,0 +1,21 @@
1
+ require 'em-fs/file/stat'
2
+
3
+ module EventMachine
4
+ class File
5
+
6
+ class << self
7
+
8
+ def stat path, &block
9
+ EM::SystemCommand.execute 'stat', [:format, EM::File::Stat::STAT_FORMAT], path do |on|
10
+ on.success do |ps|
11
+ block.call EM::File::Stat.parse ps.stdout.output
12
+ end
13
+ on.failure do |ps|
14
+ raise "EM::File::stat failed. Output:\n#{ps.stderr.output}"
15
+ end
16
+ end
17
+ end
18
+
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,149 @@
1
+ module EventMachine
2
+ class FileUtils
3
+ class << self
4
+ ##
5
+ # Make directories.
6
+ def mkdir *dirs, &block
7
+ options = { parents: false }.merge dirs.extract_options!
8
+ cmd = EM::SystemCommand.new 'mkdir', &block
9
+ cmd << :p if options[:parents]
10
+ cmd << dirs
11
+ cmd.execute
12
+ end
13
+
14
+ ##
15
+ # Make directories with parents.
16
+ def mkdir_p *dirs, &block
17
+ options = {}.merge dirs.extract_options!
18
+ mkdir *dirs, options.merge(parents: true), &block
19
+ end
20
+
21
+ ##
22
+ # Remove the directories if they are empty.
23
+ def rmdir *dirs, &block
24
+ options = { parents: false }.merge dirs.extract_options!
25
+ cmd = EM::SystemCommand.new 'rmdir'
26
+ cmd << :p if options[:parents]
27
+ cmd << dirs
28
+ cmd.execute &block
29
+ end
30
+
31
+ ##
32
+ # Create link in file system.
33
+ def ln src, dest, options = {}, &block
34
+ options = { symbolic: false, force: false }.merge options
35
+ cmd = EM::SystemCommand.new 'ln'
36
+ cmd << :s if options[:symbolic]
37
+ cmd << :f if options[:force]
38
+ cmd << src << dest
39
+ cmd.execute &block
40
+ end
41
+
42
+ ##
43
+ # Create symbolic link.
44
+ def ln_s src, dest, options = {}, &block
45
+ ln src, dest, options.merge(symbolic: true), &block
46
+ end
47
+
48
+ ##
49
+ # Force symbolic link creation.
50
+ def ln_sf src, dest, options = {}, &block
51
+ ln src, dest, options.merge(symbolic: true, force: true), &block
52
+ end
53
+
54
+ ##
55
+ # Copy files.
56
+ def cp *args, &block
57
+ options = { recursive: false }.merge args.extract_options!
58
+ unless args.length >= 2
59
+ raise 'Too few arguments. Need source and destination at least.'
60
+ end
61
+
62
+ cmd = EM::SystemCommand.new 'cp'
63
+ cmd << :r if options[:recursive]
64
+ cmd << args
65
+ cmd.execute &block
66
+ end
67
+
68
+ ##
69
+ # Recursively copy files.
70
+ def cp_r *args, &block
71
+ options = { recursive: false }.merge args.extract_options!
72
+ cp *args, options.merge(recursive: true), &block
73
+ end
74
+
75
+ ##
76
+ # Move files or directories.
77
+ def mv *args, &block
78
+ options = { recursive: false }.merge args.extract_options!
79
+ unless args.length >= 2
80
+ raise 'Too few arguments. Need source and destination at least.'
81
+ end
82
+
83
+ cmd = EM::SystemCommand.new 'mv'
84
+ cmd << args
85
+ cmd.execute &block
86
+ end
87
+
88
+ ##
89
+ # Remove files or directories.
90
+ def rm *args, &block
91
+ options = { recursive: false, force: false }.merge args.extract_options!
92
+ cmd = EM::SystemCommand.new 'rm'
93
+ cmd << '-r' if options[:recursive]
94
+ cmd << '-f' if options[:force]
95
+ cmd << args
96
+ cmd.execute &block
97
+ end
98
+
99
+ def rm_r target, options = {}, &block
100
+ rm target, options.merge(recursive: true), &block
101
+ end
102
+
103
+ def rm_rf target, options = {}, &block
104
+ rm target, options.merge(recursive: true, force: true), &block
105
+ end
106
+
107
+ def install *args, &block
108
+ options = { mode: '755' }.merge args.extract_options!
109
+ cmd = EM::SystemCommand.new 'install'
110
+ cmd.add '--mode', options[:mode] if options[:mode]
111
+ cmd << args
112
+ cmd.execute &block
113
+ end
114
+
115
+ def chmod mode, *dest, &block
116
+ options = { recursive: false }.merge dest.extract_options!
117
+ cmd = EM::SystemCommand.new 'chmod'
118
+ cmd << :R if options[:recursive]
119
+ cmd << mode << dest
120
+ cmd.execute &block
121
+ end
122
+
123
+ def chmod_R mode, *dest, &block
124
+ options = { recursive: false }.merge dest.extract_options!
125
+ chmod mode, *dest, options.merge(recursive: true), &block
126
+ end
127
+
128
+ def chown user, group, *dest, &block
129
+ options = { recursive: false }.merge dest.extract_options!
130
+ cmd = EM::SystemCommand.new 'chown'
131
+ cmd << :R if options[:recursive]
132
+ cmd << "#{user.to_s}:#{group.to_s}" << dest
133
+ cmd.execute &block
134
+ end
135
+
136
+ def chown_R user, group, *dest, &block
137
+ options = { recursive: false }.merge dest.extract_options!
138
+ chown user, group, dest, options.merge(recursive: true), &block
139
+ end
140
+
141
+ def touch *dest, &block
142
+ options = {}.merge dest.extract_options!
143
+ cmd = EM::SystemCommand.new 'touch'
144
+ cmd << dest
145
+ cmd.execute &block
146
+ end
147
+ end
148
+ end
149
+ end
@@ -0,0 +1,58 @@
1
+ # -*- coding: utf-8 -*-
2
+ module EventMachine
3
+ class FS
4
+ class Command < EM::SystemCommand
5
+
6
+ PROGRESS_REGEXP = /([A-Za-z0-9\.\-\/]+)\n[ ]+(\d+)/.freeze
7
+
8
+ ##
9
+ # Invokes `#execute` of super-class and adds a progress matcher.
10
+ def execute &block
11
+ super &block
12
+
13
+ stdout.match PROGRESS_REGEXP, match: :last, in: :output do |file, bytes|
14
+ receive_progress file, bytes.to_i
15
+ end
16
+
17
+ self
18
+ end
19
+
20
+ ##
21
+ # Is called when ever a `EM::FilesystemCommand` stdout updates the line
22
+ # is matched the `EM::FilesystemCommand::PROGRESS_REGEXP`.
23
+ #
24
+ # Calls all defined callbacks for progress events.
25
+ #
26
+ # @param [String] file The file that´s been updated.
27
+ # @param [Integer] bytes The bytes moved or copied.
28
+ def receive_progress file, bytes
29
+ progress_callbacks.each do |cb|
30
+ cb.call file, bytes
31
+ end
32
+ end
33
+
34
+ ##
35
+ # Defines a progress callback.
36
+ #
37
+ # @yield The block to be stored as callback for progress events.
38
+ # @yieldparam [String] file The file that´s been updated.
39
+ # @yieldparam [Integer] bytes The bytes moved or copied.
40
+ def progress &block
41
+ progress_callbacks << block
42
+ end
43
+
44
+ ##
45
+ # The callbacks for progress events.
46
+ #
47
+ # @return [Array] The array of callbacks for progress events.
48
+ private
49
+ def progress_callbacks
50
+ @progress_callbacks ||= []
51
+ end
52
+
53
+ def progress_regexp
54
+ @progress_regexp ||= /([A-Za-z0-9\.\-\/]+)\n[ ]+(\d+)/.freeze
55
+ end
56
+ end
57
+ end
58
+ end
@@ -0,0 +1,11 @@
1
+ module EventMachine
2
+ class FS
3
+ class RsyncCommand < EM::FS::Command
4
+
5
+ def initialize
6
+ super 'rsync'
7
+ end
8
+
9
+ end
10
+ end
11
+ end
data/lib/em-fs/fs.rb ADDED
@@ -0,0 +1,25 @@
1
+ require 'em-fs/fs/command'
2
+ require 'em-fs/fs/rsync_command'
3
+
4
+ module EventMachine
5
+ class FS
6
+ class << self
7
+
8
+ def rsync *args, &block
9
+ options = { }.merge args.extract_options!
10
+ cmd = EM::FS::RsyncCommand.new
11
+ cmd << :progress
12
+ cmd << args
13
+ cmd.execute &block
14
+ end
15
+
16
+ def find *args, &block
17
+ options = { }.merge args.extract_options!
18
+ cmd = EM::SystemCommand.new 'find'
19
+ cmd << args
20
+ cmd.execute &block
21
+ end
22
+
23
+ end
24
+ end
25
+ end