mediakit 0.0.1 → 0.0.2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: ba4ab75bf6e7d06e4d47117147e26dd2dccdb650
4
- data.tar.gz: d4e1e172178d66a94c581696e00235a896567cf0
3
+ metadata.gz: 6bce22e6bb5655d6ef5522dfb86cd95660b56119
4
+ data.tar.gz: 4ae5b7f5a0c1348aa22de26b0da11a80c47f0f05
5
5
  SHA512:
6
- metadata.gz: 02b9db5afc15386e6398f267513cb5c7b040e540e7f6f677f5b9d9f70d410b49c16a28cea77a3006df674a95ce67d2e5ef8209629ce69e38c16bb52da3acdcb7
7
- data.tar.gz: b42d2eb275b21769af3c90e3a8df77220cdd81abe5bc060f10912995ec6d2e0ffa230dba12f43eb34f036373aeacf7575e2e779b4d505f0c7878dd6405fd5b9b
6
+ metadata.gz: 67789568de47730bc876c7be8971d45bfa6e69179cb227abd4052a390e41aea7eb52939932b144a27bcc2752abe02c690361e88c8e8b9f5973ae3a2897d8ed54
7
+ data.tar.gz: 8db964b6558ceec920bc45833bcb7e57cccc1a5f6891c69540c40b3934a35761feb7d02f440f0abb0bbfda304bf463c02de0b20b3d21cab73f8854032dc751ef
data/.travis.yml CHANGED
@@ -1,3 +1,7 @@
1
1
  language: ruby
2
2
  rvm:
3
3
  - 2.2.0
4
+ before_install:
5
+ - gem update --system
6
+ - gem update bundler
7
+ - gem --version
data/README.md CHANGED
@@ -1,5 +1,7 @@
1
1
  # Mediakit
2
2
 
3
+ [![Build Status](https://travis-ci.org/ainame/mediakit.svg)](https://travis-ci.org/ainame/mediakit)
4
+
3
5
  mediakit is the libraries for ffmpeg and sox backed media manipulation something.
4
6
  I've design this library for following purpose.
5
7
 
@@ -8,7 +10,10 @@ I've design this library for following purpose.
8
10
 
9
11
  ## Development Plan
10
12
 
13
+ Currently under development.
14
+
11
15
  * [x] low-level interface for ffmpeg
16
+ * [ ] low-level interface's basic feature
12
17
  * [ ] high-level interface for ffmpeg
13
18
  * [ ] low-level interface for sox
14
19
  * [ ] high-level interface for sox
@@ -46,18 +51,18 @@ but can pass certain it.
46
51
 
47
52
  ```rb
48
53
  driver = Mediakit::Drivers::FFmpeg.new
49
- ffmpeg = Mediakit::Runners::FFmpeg.new(driver)
54
+ ffmpeg = Mediakit::FFmpeg.new(driver)
50
55
 
51
- options = Mediakit::Runners::FFmpeg::Options.new(
52
- Mediakit::Runners::FFmpeg::Options::GlobalOption.new(
56
+ options = Mediakit::FFmpeg::Options.new(
57
+ Mediakit::FFmpeg::Options::GlobalOption.new(
53
58
  't' => 100,
54
59
  'y' => true,
55
60
  ),
56
- Mediakit::Runners::FFmpeg::Options::InputFileOption.new(
61
+ Mediakit::FFmpeg::Options::InputFileOption.new(
57
62
  options: nil,
58
63
  path: input,
59
64
  ),
60
- Mediakit::Runners::FFmpeg::Options::OutputFileOption.new(
65
+ Mediakit::FFmpeg::Options::OutputFileOption.new(
61
66
  options: {
62
67
  'vf' => 'crop=320:320:0:0',
63
68
  'ar' => '44100',
@@ -66,7 +71,7 @@ options = Mediakit::Runners::FFmpeg::Options.new(
66
71
  path: output,
67
72
  ),
68
73
  )
69
- puts "$ ffmpeg #options"
74
+ puts "$ #{ffmpeg.command(options)}"
70
75
  puts ffmpeg.run(options)
71
76
  ```
72
77
 
data/Rakefile CHANGED
@@ -1 +1,16 @@
1
- require "bundler/gem_tasks"
1
+ require 'rake'
2
+ require 'rake/testtask'
3
+ require 'bundler/gem_tasks'
4
+ require 'yard'
5
+ require 'yard/rake/yardoc_task'
6
+
7
+ Rake::TestTask.new do |t|
8
+ t.libs << 'test'
9
+ t.test_files = FileList['test/**/test_*.rb']
10
+ end
11
+
12
+ task(default: :test)
13
+
14
+ YARD::Rake::YardocTask.new do |t|
15
+ t.files = ['lib/**/*.rb']
16
+ end
@@ -1,9 +1,10 @@
1
1
  require 'shellwords'
2
- require 'mediakit/utils/popen_helper'
2
+ require 'mediakit/utils/process_runner'
3
3
 
4
4
  module Mediakit
5
5
  module Drivers
6
6
  class DriverError < StandardError; end
7
+ class FailError < DriverError; end
7
8
  class ConfigurationError < DriverError; end
8
9
 
9
10
  class Base
@@ -25,18 +26,21 @@ module Mediakit
25
26
  # execute command and return result
26
27
  #
27
28
  # @overload run(args)
28
- # @param args [String] arguments for command
29
- # @overload run(*args)
30
- # @param args [Array] arguments for command
31
- # @return result [Bool] runners result
29
+ # @param [String] args string argument for command
30
+ # @overload run(*args, options)
31
+ # @param [Array] args arguments for command
32
+ # @option [Hash] options run options
33
+ # @return [Bool] stdout output
32
34
  def run(*args)
35
+ options = (args.last && args.last.kind_of?(Hash)) ? args.pop : {}
33
36
  begin
34
- escaped_args = Mediakit::Utils::PopenHelper.escape(*args)
35
- Mediakit::Utils::PopenHelper.run(bin, escaped_args)
36
- rescue Mediakit::Utils::PopenHelper::CommandNotFoundError => e
37
+ escaped_args = Mediakit::Utils::ProcessRunner.escape(*args)
38
+ runner = Mediakit::Utils::ProcessRunner.new(options)
39
+ stdout, stderr, exit_status = runner.run(bin, escaped_args)
40
+ raise(FailError, stderr) unless exit_status
41
+ stdout
42
+ rescue Mediakit::Utils::ProcessRunner::CommandNotFoundError => e
37
43
  raise(ConfigurationError, "cant' find bin in #{bin}.")
38
- rescue => e
39
- raise(DriverError, "#{self.class} catch error with command(#{Mediakit::Utils::PopenHelper.command(bin,escaped_args)}) - #{e.message}, #{e.backtrace.join("\n")}")
40
44
  end
41
45
  end
42
46
 
@@ -46,9 +50,9 @@ module Mediakit
46
50
  # @param args [String] arguments for command
47
51
  # @overload run(*args)
48
52
  # @param args [Array] arguments for command
49
- # @return result [String] runners to execute
53
+ # @return [String] command
50
54
  def command(*args)
51
- escaped_args = Mediakit::Utils::PopenHelper.escape(*args)
55
+ escaped_args = Mediakit::Utils::ProcessRunner.escape(*args)
52
56
  "#{bin} #{escaped_args}"
53
57
  end
54
58
  end
@@ -58,18 +62,19 @@ module Mediakit
58
62
  #
59
63
  # @overload run(args)
60
64
  # @param args [String] arguments for command
61
- # @overload run(*args)
65
+ # @overload run(*args, options)
62
66
  # @param args [Array] arguments for command
63
- # @return result [Bool] runners result
67
+ # @option options [Hash] run options
68
+ # @return [Bool] stdout output
64
69
  def run(args = '')
65
70
  begin
66
71
  # Force escape args string on here,
67
72
  # because this design can't use Cocaine::CommandLine's safety solution.
68
- escaped_args = Mediakit::Utils::PopenHelper.escape(args.dup)
73
+ escaped_args = Mediakit::Utils::ProcessRunner.escape(args.dup)
69
74
  command_line = Cocaine::CommandLine.new(bin, escaped_args, swallow_stderr: true)
70
75
  command_line.run
71
- rescue => e
72
- raise(DriverError, "#{self.class} catch error with runners [$ #{command_line.command}] - #{e.message}, #{e.backtrace.join("\n")}")
76
+ rescue Cocaine::ExitStatusError => e
77
+ raise(FailError, e.message)
73
78
  end
74
79
  end
75
80
 
@@ -79,7 +84,7 @@ module Mediakit
79
84
  # @param args [String] arguments for command
80
85
  # @overload run(*args)
81
86
  # @param args [Array] arguments for command
82
- # @return result [String] runners to execute
87
+ # @return [String] command commands to execute
83
88
  def command(args = '')
84
89
  Cocaine::CommandLine.new(bin, args).command
85
90
  end
@@ -126,12 +131,15 @@ module Mediakit
126
131
  end
127
132
  end
128
133
 
134
+ # factory class for ffmpeg driver
129
135
  class FFmpeg < AbstractFactory
130
136
  end
131
137
 
138
+ # factory class for ffprobe driver
132
139
  class FFprobe < AbstractFactory
133
140
  end
134
141
 
142
+ # factory class for sox driver
135
143
  class Sox < AbstractFactory
136
144
  end
137
145
  end
@@ -0,0 +1,29 @@
1
+ module Mediakit
2
+ class FFmpeg
3
+ module Introspection
4
+ DELIMITER_FOR_CODECS = "\n -------\n".freeze
5
+ DELIMITER_FOR_FORMATS = "\n --\n".freeze
6
+ DELIMITER_FOR_CODER = "\n ------\n".freeze
7
+
8
+ def codecs
9
+ @codecs ||= run(global_options('codecs')).split(DELIMITER_FOR_CODECS)[1].each_line.to_a
10
+ end
11
+
12
+ def formats
13
+ @formats ||= run(global_options('formats')).split(DELIMITER_FOR_FORMATS)[1].each_line.to_a
14
+ end
15
+
16
+ def decoders
17
+ @decoders ||= run(global_options('decoders')).split(DELIMITER_FOR_CODER)[1].each_line.to_a
18
+ end
19
+
20
+ def encoders
21
+ @encoders ||= run(global_options('encoders')).split(DELIMITER_FOR_CODER)[1].each_line.to_a
22
+ end
23
+
24
+ def global_options(flag)
25
+ Options.new(Options::GlobalOption.new(flag => true))
26
+ end
27
+ end
28
+ end
29
+ end
@@ -9,11 +9,10 @@ module Mediakit
9
9
  #
10
10
  class Options
11
11
  attr_reader(:global, :inputs, :output)
12
- # constructor
13
- #
14
- # @option args [Mediakit::FFmpeg::Options::GlobalOption]
15
- # @option args [Array<Mediakit::FFmpeg::Options::InputFileOption>] array object Mediakit::FFmpeg::Options::InputOption
16
- # @option args [Mediakit::FFmpeg::Options::OutputFileOption]
12
+
13
+ # @option [Mediakit::FFmpeg::Options::GlobalOption] args option
14
+ # @option [Mediakit::FFmpeg::Options::InputFileOption] args Mediakit::FFmpeg::Options::InputOption
15
+ # @option [Mediakit::FFmpeg::Options::OutputFileOption] args output file option
17
16
  def initialize(*args)
18
17
  @global, @inputs, @output = nil, [], nil
19
18
  args.each do |option|
@@ -61,9 +60,7 @@ module Mediakit
61
60
 
62
61
  # Base class for Options
63
62
  class OrderedHash < ActiveSupport::OrderedHash
64
- # initializer
65
- #
66
- # @param options [Hash] initial option values
63
+ # @param [Hash] options initial option values
67
64
  def initialize(options = {})
68
65
  options.each { |key, value| raise_if_invalid_arg_error(key, value) } if options
69
66
  self.merge!(options) if options && options.kind_of?(Hash)
@@ -119,8 +116,8 @@ module Mediakit
119
116
  end
120
117
 
121
118
  class InputFileOption < OptionPathPair
122
- # @param options [Hash] input options
123
- # @param path [String] input file path
119
+ # @param [Hash] :options input options
120
+ # @param [String] :path input file path
124
121
  def initialize(options:, path:)
125
122
  ordered_hash = OrderedHash.new(options)
126
123
  super(options: ordered_hash, path: path)
@@ -132,8 +129,8 @@ module Mediakit
132
129
  end
133
130
 
134
131
  class OutputFileOption < OptionPathPair
135
- # @param options [Hash] output options
136
- # @param path [String] output file path
132
+ # @param [Hash] :options output options
133
+ # @param [String] :path output file path
137
134
  def initialize(options:, path:)
138
135
  ordered_hash = OrderedHash.new(options)
139
136
  super(options: ordered_hash, path: path)
@@ -144,23 +141,14 @@ module Mediakit
144
141
  end
145
142
  end
146
143
 
147
- class InputFileOptionCollection
148
- attr_reader(:input_file_options)
149
-
150
- # @param *input_file_options [Mediakit::FFmpeg::InputFileOptions]
151
- def initialize(*input_file_options)
152
- @options = input_file_options
153
- end
154
-
155
- def empty?
156
- @options.empty?
144
+ class QuoteString
145
+ def initialize(string)
146
+ @string = string
157
147
  end
158
148
 
159
- def compose
160
- @options.map(&:compose).join(' ')
149
+ def to_s
150
+ "\"#{@string}\""
161
151
  end
162
-
163
- alias_method :to_s, :compose
164
152
  end
165
153
 
166
154
  # see https://www.ffmpeg.org/ffmpeg.html#Stream-specifiers-1
@@ -1,14 +1,12 @@
1
- require 'mediakit/ffmpeg/options'
2
1
  require 'mediakit/drivers'
2
+ require 'mediakit/ffmpeg/options'
3
+ require 'mediakit/ffmpeg/introspection'
3
4
 
4
5
  module Mediakit
5
6
  class FFmpeg
6
- class FFmpegError < StandardError;
7
- end
7
+ include Introspection
8
+ class FFmpegError < StandardError; end
8
9
 
9
- DELIMITER_FOR_CODECS = "\n -------\n".freeze
10
- DELIMITER_FOR_FORMATS = "\n --\n".freeze
11
- DELIMITER_FOR_CODER = "\n ------\n".freeze
12
10
 
13
11
  def initialize(driver)
14
12
  @driver = driver
@@ -16,7 +14,7 @@ module Mediakit
16
14
 
17
15
  # execute runners with options object
18
16
  #
19
- # @param options [Mediakit::Runners::FFmpeg::Options] options object to create CLI argument
17
+ # @param [Mediakit::Runners::FFmpeg::Options] options options to create CLI argument
20
18
  def run(options)
21
19
  args = options.compose
22
20
  execute(args)
@@ -27,38 +25,10 @@ module Mediakit
27
25
  @driver.command(args)
28
26
  end
29
27
 
30
- def codecs
31
- @codecs ||= run(global_options('codecs')).split(DELIMITER_FOR_CODECS)[1].each_line.to_a
32
- end
33
-
34
- def formats
35
- @formats ||= run(global_options('formats')).split(DELIMITER_FOR_FORMATS)[1].each_line.to_a
36
- end
37
-
38
- def decoders
39
- @decoders ||= run(global_options('decoders')).split(DELIMITER_FOR_CODER)[1].each_line.to_a
40
- end
41
-
42
- def encoders
43
- @encoders ||= run(global_options('encoders')).split(DELIMITER_FOR_CODER)[1].each_line.to_a
44
- end
45
-
46
28
  private
47
29
 
48
30
  def execute(args = '')
49
- begin
50
- @driver.run(args)
51
- rescue Drivers::DriverError => e
52
- raise(FFmpegError, "#catch driver's error - #{e.message}, #{e.backtrace.join("\n")}")
53
- end
54
- end
55
-
56
- def global_options(flag)
57
- Mediakit::FFmpeg::Options.new(
58
- Mediakit::FFmpeg::Options::GlobalOptions.new(
59
- flag => true,
60
- ),
61
- )
31
+ @driver.run(args)
62
32
  end
63
33
  end
64
34
  end
@@ -10,11 +10,7 @@ module Mediakit
10
10
  end
11
11
 
12
12
  def execute(args = '')
13
- begin
14
- driver.run(args)
15
- rescue => e
16
- raise(FFprobeError, "#{self.class} catch error - #{e.message}, #{e.backtrace.join("\n")}")
17
- end
13
+ driver.run(args)
18
14
  end
19
15
 
20
16
  def get_json(path)
@@ -0,0 +1,159 @@
1
+ require 'shellwords'
2
+ require 'open3'
3
+ require 'thread'
4
+ require 'timeout'
5
+
6
+
7
+ module Mediakit
8
+ module Utils
9
+ class ProcessRunner
10
+ class CommandNotFoundError < StandardError;
11
+ end
12
+ class TimeoutError < StandardError;
13
+ end
14
+
15
+ def initialize(timeout: nil)
16
+ @timeout = timeout
17
+ end
18
+
19
+ # @overload run(command, *args)
20
+ # @param command [String]
21
+ # @param args [Array] args as array for safety shellescape
22
+ # @overload run(command, args)
23
+ # @param command [String] command name
24
+ # @param args [Array] args as string
25
+ # @return out [String] stdout of command
26
+ # @return err [String] stderr of command
27
+ # @return exit_status [Boolean] is succeeded
28
+ def run(bin, *args)
29
+ command = self.class.command(bin, *args)
30
+
31
+ pid, out, err, exit_status = nil
32
+ out_reader, err_reader = nil
33
+ watch = TimeoutWatch.new(@timeout)
34
+ begin
35
+ stdin, stdout, stderr, wait_thr = Open3.popen3(command)
36
+ stdin.close
37
+ pid = wait_thr.pid
38
+ watch.start(Thread.current)
39
+ out_reader = IOReader.new(stdout) { |chunk| watch.update }
40
+ err_reader = IOReader.new(stderr) { |chunk| watch.update }
41
+
42
+ wait_thr.join
43
+ exit_status = (wait_thr.value.exitstatus == 0)
44
+ rescue Errno::ENOENT => e
45
+ raise(CommandNotFoundError, "Can't find command - #{command}, #{e.meessage}")
46
+ rescue Timeout::Error => error
47
+ Process.kill('SIGKILL', pid)
48
+ raise(error)
49
+ ensure
50
+ out_reader.finish
51
+ err_reader.finish
52
+ watch.finish
53
+ end
54
+
55
+ [out_reader.data, err_reader.data, exit_status]
56
+ end
57
+
58
+ def self.command(bin, *args)
59
+ escaped_args = escape(*args)
60
+ "#{bin} #{escaped_args}"
61
+ end
62
+
63
+ def self.escape(*args)
64
+ case args.size
65
+ when 1
66
+ escape_with_split(args[0])
67
+ else
68
+ Shellwords.join(args.map { |x| Shellwords.escape(x) })
69
+ end
70
+ end
71
+
72
+ private
73
+
74
+ def self.escape_with_split(string)
75
+ splits = Shellwords.split(string)
76
+ splits = splits.map { |x| Shellwords.escape(x) }
77
+ splits.join(' ')
78
+ end
79
+
80
+ class IOReader
81
+ attr_reader(:data)
82
+
83
+ def initialize(io, &block)
84
+ raise(ArgumentError) unless block_given?
85
+ @io = io
86
+ @data = ''
87
+ @block = block
88
+ start
89
+ end
90
+
91
+ def finish
92
+ @thread.join
93
+ @thread.kill
94
+ end
95
+
96
+ private
97
+ def start
98
+ @thread = Thread.new { read }
99
+ nil
100
+ end
101
+
102
+ def read
103
+ return if @io.closed?
104
+ begin
105
+ while chunk = @io.gets
106
+ @data << chunk
107
+ @block.call(chunk) if @block
108
+ end
109
+ rescue IOError => e
110
+ warn "[WARN] IOError #{e.message}"
111
+ ensure
112
+ @io.close unless @io.closed?
113
+ end
114
+ end
115
+ end
116
+
117
+ # watch process progress by io.
118
+ # when wait time exceed duration, then kill process.
119
+ class TimeoutWatch
120
+ attr_reader(:duration)
121
+
122
+ def initialize(duration)
123
+ @duration = duration
124
+ @watched_at = Time.now
125
+ @mutex = Mutex.new
126
+ end
127
+
128
+ def start(current_thread, &block)
129
+ @current_thread = current_thread
130
+ @watch_thread = Thread.new do
131
+ loop do
132
+ if timeout?
133
+ @current_thread.raise(Timeout::Error, "wait timeout error with #{duration} sec.")
134
+ end
135
+ sleep(0.1)
136
+ end
137
+ end
138
+ nil
139
+ end
140
+
141
+ def finish
142
+ @watch_thread.kill
143
+ end
144
+
145
+ def update
146
+ @mutex.synchronize do
147
+ @watched_at = Time.now
148
+ end
149
+ end
150
+
151
+ private
152
+
153
+ def timeout?
154
+ (Time.now - @watched_at) > duration
155
+ end
156
+ end
157
+ end
158
+ end
159
+ end
@@ -1,3 +1,3 @@
1
1
  module Mediakit
2
- VERSION = "0.0.1"
2
+ VERSION = "0.0.2"
3
3
  end
data/mediakit.gemspec CHANGED
@@ -24,8 +24,8 @@ EOS
24
24
 
25
25
  spec.add_runtime_dependency "cocaine", "~> 0.5.7"
26
26
  spec.add_runtime_dependency "activesupport", "~> 4"
27
- spec.add_development_dependency "bundler", "~> 1.9"
28
27
  spec.add_development_dependency "rake", "~> 10.0"
29
- spec.add_development_dependency "pry", "~> 0.10"
28
+ spec.add_development_dependency "pry", '~> 0.10'
30
29
  spec.add_development_dependency "ruby-debug-ide", "~> 0.4"
30
+ spec.add_development_dependency "yard", "> 0.8"
31
31
  end
@@ -0,0 +1,9 @@
1
+ require 'mediakit'
2
+
3
+ root = File.expand_path(File.join(File.dirname(__FILE__), '../'))
4
+ Mediakit::Drivers::FFmpeg.configure do |config|
5
+ config.bin_path = File.join(root, 'test/supports/ffmpeg')
6
+ end
7
+
8
+ driver = Mediakit::Drivers::FFmpeg.new
9
+ puts driver.run('-version')
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mediakit
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1
4
+ version: 0.0.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - ainame
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2015-05-10 00:00:00.000000000 Z
11
+ date: 2015-05-12 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: cocaine
@@ -38,20 +38,6 @@ dependencies:
38
38
  - - "~>"
39
39
  - !ruby/object:Gem::Version
40
40
  version: '4'
41
- - !ruby/object:Gem::Dependency
42
- name: bundler
43
- requirement: !ruby/object:Gem::Requirement
44
- requirements:
45
- - - "~>"
46
- - !ruby/object:Gem::Version
47
- version: '1.9'
48
- type: :development
49
- prerelease: false
50
- version_requirements: !ruby/object:Gem::Requirement
51
- requirements:
52
- - - "~>"
53
- - !ruby/object:Gem::Version
54
- version: '1.9'
55
41
  - !ruby/object:Gem::Dependency
56
42
  name: rake
57
43
  requirement: !ruby/object:Gem::Requirement
@@ -94,6 +80,20 @@ dependencies:
94
80
  - - "~>"
95
81
  - !ruby/object:Gem::Version
96
82
  version: '0.4'
83
+ - !ruby/object:Gem::Dependency
84
+ name: yard
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">"
88
+ - !ruby/object:Gem::Version
89
+ version: '0.8'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">"
95
+ - !ruby/object:Gem::Version
96
+ version: '0.8'
97
97
  description: |
98
98
  mediakit is the libraries for ffmpeg and sox backed media manipulation something.
99
99
  you can create complex manipulation for media as a ruby code.
@@ -113,11 +113,13 @@ files:
113
113
  - lib/mediakit.rb
114
114
  - lib/mediakit/drivers.rb
115
115
  - lib/mediakit/ffmpeg.rb
116
+ - lib/mediakit/ffmpeg/introspection.rb
116
117
  - lib/mediakit/ffmpeg/options.rb
117
118
  - lib/mediakit/ffprobe.rb
118
- - lib/mediakit/utils/popen_helper.rb
119
+ - lib/mediakit/utils/process_runner.rb
119
120
  - lib/mediakit/version.rb
120
121
  - mediakit.gemspec
122
+ - sample/configure.rb
121
123
  - sample/raw_crop.rb
122
124
  - templates/codec.rb.erb
123
125
  - templates/decoder.rb.erb
@@ -142,8 +144,9 @@ required_rubygems_version: !ruby/object:Gem::Requirement
142
144
  version: '0'
143
145
  requirements: []
144
146
  rubyforge_project:
145
- rubygems_version: 2.4.5
147
+ rubygems_version: 2.4.6
146
148
  signing_key:
147
149
  specification_version: 4
148
150
  summary: mediakit is the libraries for ffmpeg and sox backed media manipulation something.
149
151
  test_files: []
152
+ has_rdoc:
@@ -1,68 +0,0 @@
1
- require 'shellwords'
2
- require 'open3'
3
-
4
- module Mediakit
5
- module Utils
6
- module PopenHelper
7
-
8
- class CommandNotFoundError < StandardError;
9
- end
10
-
11
- # @overload run(command, *args)
12
- # @param command [String]
13
- # @param args [Array] args as array for safety shellescape
14
- # @overload run(command, args)
15
- # @param command [String] command name
16
- # @param args [Array] args as string
17
- # @return out [String] stdout of command
18
- # @return err [String] stderr of command
19
- # @return exit_status [Boolean] is succeeded
20
- def run(bin, *args)
21
- command = command(bin, *args)
22
-
23
- out, err, exit_status = nil
24
- begin
25
- Open3.popen3(command) do |stdin, stdout, stderr, wait_thr|
26
- stdin.close
27
- out = stdout.read
28
- err = stderr.read
29
- exit_status = (wait_thr.value.exitstatus == 0)
30
- end
31
- rescue Errno::ENOENT => e
32
- raise(CommandNotFoundError, "Can't find command - #{command}, #{e.meessage}")
33
- end
34
-
35
- [out, err, exit_status]
36
- end
37
-
38
- module_function(:run)
39
-
40
- def command(bin, *args)
41
- escaped_args = escape(*args)
42
- "#{bin} #{escaped_args}"
43
- end
44
-
45
- module_function(:command)
46
-
47
- def escape(*args)
48
- case args.size
49
- when 1
50
- _escape_with_split(args[0])
51
- else
52
- Shellwords.join(args.map { |x| Shellwords.escape(x) })
53
- end
54
- end
55
-
56
- module_function(:escape)
57
-
58
- def _escape_with_split(string)
59
- splits = Shellwords.split(string)
60
- splits = splits.map { |x| Shellwords.escape(x) }
61
- splits.join(' ')
62
- end
63
-
64
- module_function(:_escape_with_split)
65
-
66
- end
67
- end
68
- end