customresource-elastictranscoder 0.7.2

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,2 @@
1
+ ore-apachev2
2
+ ============
@@ -0,0 +1,30 @@
1
+ # encoding: utf-8
2
+
3
+ require 'rubygems'
4
+
5
+ begin
6
+ require 'bundler'
7
+ rescue LoadError => e
8
+ warn e.message
9
+ warn "Run `gem install bundler` to install Bundler."
10
+ exit -1
11
+ end
12
+
13
+ # begin
14
+ # Bundler.setup(:development)
15
+ # rescue Bundler::BundlerError => e
16
+ # warn e.message
17
+ # warn "Run `bundle install` to install missing gems."
18
+ # exit e.status_code
19
+ # end
20
+
21
+ require 'rake'
22
+
23
+ require 'rubygems/tasks'
24
+ Gem::Tasks.new
25
+
26
+ require 'cucumber/rake/task'
27
+
28
+ Cucumber::Rake::Task.new do |t|
29
+ t.cucumber_opts = %w[--format pretty]
30
+ end
@@ -0,0 +1,16 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ # Adjust lib path
4
+ _lib=File.expand_path(File.dirname(__FILE__) + '/../lib')
5
+ $:.unshift(_lib) unless $:.include?(_lib)
6
+ require 'customresource/elastictranscoder/cli'
7
+
8
+ # =====================================================================================================================
9
+ rc = CustomResource::ElasticTranscoder::Cli.start(ARGV)
10
+ if rc.is_a?(Fixnum)
11
+ exit rc
12
+ else
13
+ puts rc.ai
14
+ exit 0
15
+ end
16
+
@@ -0,0 +1,33 @@
1
+ # -*- encoding: utf-8 -*-
2
+
3
+ require File.expand_path('../lib/customresource/elastictranscoder/version', __FILE__)
4
+
5
+ Gem::Specification.new do |gem|
6
+ gem.name = 'customresource-elastictranscoder'
7
+ gem.version = CustomResource::ElasticTranscoder::VERSION
8
+ gem.summary = %q{An action command for aws-cfn-resource-bridge to implement CloudFormation custom resources}
9
+ gem.description = %q{An action command for aws-cfn-resource-bridge to implement CloudFormation custom resources}
10
+ gem.license = 'Apachev2'
11
+ gem.authors = ['Christo De Lange']
12
+ gem.email = 'rubygems@dldinternet.com'
13
+ gem.homepage = 'https://rubygems.org/gems/customresource-elastictranscoder'
14
+
15
+ gem.files = `git ls-files`.split($/)
16
+ gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
17
+ gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
18
+ gem.require_paths = ['lib']
19
+
20
+ gem.add_development_dependency 'bundler', '~> 1.0'
21
+ gem.add_development_dependency 'rake', '~> 10.1.0'
22
+ gem.add_development_dependency 'rubygems-tasks', '~> 0.2'
23
+
24
+ gem.add_dependency 'thor', '~> 0.19'
25
+ gem.add_dependency 'awesome_print', '~> 1.2'
26
+ gem.add_dependency 'colorize', '~> 0.7.3'
27
+ gem.add_dependency 'aws-sdk-core', '>= 2.0', '< 2.1'
28
+ gem.add_dependency 'inifile', '~> 3'
29
+ gem.add_dependency 'dldinternet-mixlib-thor-nocommands', '~> 0.2'
30
+ gem.add_dependency 'dldinternet-mixlib-logging', '~> 0.4'
31
+ gem.add_dependency 'customresource-base', '~> 0'
32
+
33
+ end
File without changes
@@ -0,0 +1 @@
1
+ Feature: Blah blah blah
File without changes
@@ -0,0 +1,2 @@
1
+ require 'customresource/elastictranscoder/version'
2
+ require 'customresource/elastictranscoder/cli'
@@ -0,0 +1,64 @@
1
+ require 'thor'
2
+ require 'awesome_print'
3
+ require 'colorize'
4
+ require 'aws-sdk-core'
5
+ require 'yaml'
6
+ require 'customresource/elastictranscoder/version'
7
+ require 'aws/ec2/instance_data'
8
+
9
+ module CustomResource
10
+ module ElasticTranscoder
11
+
12
+ class Cli < Thor
13
+ class_option :verbose, :type => :boolean
14
+ class_option :debug, :type => :boolean
15
+ class_option :trace, :type => :boolean
16
+ class_option :log_level, :type => :string, :banner => 'Log level ([:trace, :debug, :info, :step, :warn, :error, :fatal, :todo])'
17
+ class_option :log_file, :type => :string
18
+ class_option :inifile, :type => :string
19
+ class_option :input, :type => :string
20
+ class_option :ip_address, :type => :string
21
+
22
+ no_commands do
23
+
24
+ require 'dldinternet/mixlib/thor/no_commands'
25
+ include DLDInternet::MixLib::Thor::No_Commands
26
+
27
+ require 'customresource/elastictranscoder/mixins/cli'
28
+ include CustomResource::ElasticTranscoder::MixIns::Cli
29
+
30
+ require 'customresource/elastictranscoder/mixins/actions'
31
+ include CustomResource::ElasticTranscoder::MixIns::Actions
32
+
33
+ end # no_commands
34
+
35
+ def initialize(args = [], local_options = {}, config = {})
36
+ super(args,local_options,config)
37
+ @log_level = :step
38
+ end
39
+
40
+ desc 'version', 'display current version'
41
+ def version()
42
+ puts ::CustomResource::ElasticTranscoder::VERSION
43
+ exit 0
44
+ end
45
+
46
+ desc 'preset', 'CRUD for presets'
47
+ def preset()
48
+ process('Presets')
49
+ end
50
+
51
+ desc 'pipeline', 'CRUD for pipelines'
52
+ def pipeline()
53
+ process('Pipelines')
54
+ end
55
+
56
+ desc 'job', 'CRUD for jobs'
57
+ def job()
58
+ process('Jobs')
59
+ end
60
+
61
+ end
62
+ end
63
+ end
64
+
@@ -0,0 +1,135 @@
1
+ require 'customresource/base/mixins/actions'
2
+
3
+ module CustomResource
4
+ module ElasticTranscoder
5
+ module MixIns
6
+ module Actions
7
+ include CustomResource::Base::MixIns::Actions
8
+
9
+ def action(verb,section,proc)
10
+ prepare
11
+ # data = {}
12
+ restyp = section.gsub(/s$/,'').downcase
13
+ method = "#{verb}_#{restyp}"
14
+
15
+ resource = @event['ResourceProperties']
16
+ @logger.debug "#{method} #{resource.ai}"
17
+
18
+ # Convert the 'String' keys to :string symbols
19
+ params = properties_to_params(resource.dup)
20
+ # Weed out the invalid properties
21
+ invalid_keys = validate_params(section,params)
22
+ if invalid_keys.size > 0
23
+ @logger.warn "Invalid keys in #{params[:name] || params.ai}:\n#{invalid_keys.ai}"
24
+ end
25
+ params = delete_invalid_keys(params,invalid_keys)
26
+ # Restore these exceptions to the rule from the resource 'String' set e.g. :codec_options => { 'String': Value, }
27
+ params = restore_exception_params(section,params,resource)
28
+ @logger.debug params.ai
29
+
30
+ data = proc.call(params, restyp, method, resource)
31
+ @logger.debug data
32
+ respond('SUCCESS', data)
33
+ 0
34
+ end
35
+
36
+ def create(section)
37
+ action('create', section, lambda do |params, restyp, method, resource|
38
+ begin
39
+ data = nil
40
+ # Let's see if we have presets/pipelines which match this :name
41
+ set = []
42
+ @elastictranscoder.send("list_#{section.downcase}", { ascending: 'true' }).each do |resp|
43
+ resp.send("#{section.downcase}").map{ |item| set << item.to_h if item.name.match(/^#{params[:name]}$/) }
44
+ end
45
+ if set.size == 0
46
+ @logger.info "#{method} #{params[:name]}"
47
+ @elastictranscoder.send(method, params).each do |resp|
48
+ @logger.info resp.send(restyp).ai
49
+ data = get_item_data(resp.send(restyp).to_h, section, params)
50
+ end
51
+ else
52
+ @logger.info "Use existing #{restyp} #{params[:name]}"
53
+ data = get_item_data(set[0], section, params)
54
+ end
55
+ data
56
+ rescue Exception => e
57
+ abort! "#{restyp}/#{params[:name]}: #{e.message}"
58
+ end
59
+ end
60
+ )
61
+ end
62
+
63
+ def update(section)
64
+ action('update', section, lambda do |params, restyp, method, resource|
65
+ begin
66
+ data = nil
67
+ # Let's see if we have presets/pipelines which match this :name
68
+ set = []
69
+ @elastictranscoder.send("list_#{section.downcase}", { ascending: 'true' }).each do |resp|
70
+ resp.send("#{section.downcase}").map{ |item| set << item.to_h if item.name.match(/^#{params[:name]}$/) }
71
+ end
72
+ if set.size == 0
73
+ method = "create_#{restyp}"
74
+ @logger.info "#{method} #{params[:name]}"
75
+ @elastictranscoder.send(method, params).each do |resp|
76
+ @logger.debug resp.send(restyp).ai
77
+ data = get_item_data(resp.send(restyp).to_h, section, params)
78
+ end
79
+ else
80
+ # abort! "#{restyp}/#{params[:name]}: Resource does not exist"
81
+ # else
82
+ @logger.info "Delete existing #{restyp} #{set[0][:id]}::#{set[0][:name]}"
83
+ method = "delete_#{restyp}"
84
+ @logger.info "#{method} #{set[0][:id]}"
85
+ @elastictranscoder.send(method, { id: set[0][:id] }) #.each do |resp|
86
+ # @logger.debug resp.send(restyp).ai
87
+ # end
88
+ @logger.info "Recreate #{restyp} #{params[:name]}"
89
+ method = "create_#{restyp}"
90
+ @logger.info "#{method} #{params[:name]}"
91
+ @elastictranscoder.send(method, params).each do |resp|
92
+ @logger.debug resp.send(restyp).ai
93
+ data = get_item_data(resp.send(restyp).to_h, section, params)
94
+ end
95
+ end
96
+ data
97
+ rescue Exception => e
98
+ abort! "#{restyp}/#{params[:name]}: #{e.message}"
99
+ end
100
+ end
101
+ )
102
+ end
103
+
104
+ def delete(section)
105
+ action('delete', section, lambda do |params, restyp, method, resource|
106
+ begin
107
+ data = nil
108
+ # Let's see if we have presets/pipelines which match this :name
109
+ set = []
110
+ @elastictranscoder.send("list_#{section.downcase}", { ascending: 'true' }).each do |resp|
111
+ resp.send("#{section.downcase}").map{ |item| set << item.to_h if item.name.match(/^#{params[:name]}$/) }
112
+ end
113
+ unless set.size == 0
114
+ # abort! "#{restyp}/#{params[:name]}: Resource does not exist"
115
+ # else
116
+ @logger.info "Delete existing #{restyp} #{set[0][:id]}::#{set[0][:name]}"
117
+ method = "delete_#{restyp}"
118
+ @logger.info "#{method} #{set[0][:id]}"
119
+ @elastictranscoder.send(method, { id: set[0][:id] }) #.each do |resp|
120
+ # @logger.debug resp.send(restyp).ai
121
+ data = get_item_data({ id: set[0][:id] }.merge(resource), section, params)
122
+ # end
123
+ end
124
+ data
125
+ rescue Exception => e
126
+ abort! "#{restyp}/#{params[:name]}: #{e.message}"
127
+ end
128
+ end
129
+ )
130
+ end
131
+
132
+ end
133
+ end
134
+ end
135
+ end
@@ -0,0 +1,282 @@
1
+ require 'aws-sdk-core'
2
+ require 'customresource/base/mixins/cli'
3
+
4
+ module CustomResource
5
+ module ElasticTranscoder
6
+ module MixIns
7
+ module Cli
8
+ include CustomResource::Base::MixIns::Cli
9
+
10
+ def init_attributes
11
+ @valid_keys = {
12
+ :Presets => {
13
+ :name => nil,
14
+ :description => nil,
15
+ :container => nil,
16
+ :video => {
17
+ :codec => nil,
18
+ :codec_options => {
19
+ :'*' => nil,
20
+ },
21
+ :keyframes_max_dist => nil,
22
+ :fixed_gop => nil,
23
+ :bit_rate => nil,
24
+ :frame_rate => nil,
25
+ :max_frame_rate => nil,
26
+ :resolution => nil,
27
+ :aspect_ratio => nil,
28
+ :max_width => nil,
29
+ :max_height => nil,
30
+ :display_aspect_ratio => nil,
31
+ :sizing_policy => nil,
32
+ :padding_policy => nil,
33
+ :watermarks => {
34
+ :id => nil,
35
+ :max_width => nil,
36
+ :max_height => nil,
37
+ :sizing_policy => nil,
38
+ :horizontal_align => nil,
39
+ :horizontal_offset => nil,
40
+ :vertical_align => nil,
41
+ :vertical_offset => nil,
42
+ :opacity => nil,
43
+ :target => nil,
44
+ },
45
+ },
46
+ :audio => {
47
+ :codec => nil,
48
+ :sample_rate => nil,
49
+ :bit_rate => nil,
50
+ :channels => nil,
51
+ :codec_options => {
52
+ :profile => nil,
53
+ },
54
+ },
55
+ :thumbnails => {
56
+ :format => nil,
57
+ :interval => nil,
58
+ :resolution => nil,
59
+ :aspect_ratio => nil,
60
+ :max_width => nil,
61
+ :max_height => nil,
62
+ :sizing_policy => nil,
63
+ :padding_policy => nil,
64
+ },
65
+ },
66
+ :Pipelines => {
67
+ # required
68
+ name: nil,
69
+ # required
70
+ input_bucket: nil,
71
+ output_bucket: nil,
72
+ # required
73
+ role: nil,
74
+ notifications: {
75
+ progressing: nil,
76
+ completed: nil,
77
+ warning: nil,
78
+ error: nil,
79
+ },
80
+ content_config: {
81
+ bucket: nil,
82
+ storage_class: nil,
83
+ permissions:
84
+ {
85
+ grantee_type: nil,
86
+ grantee: nil,
87
+ access: nil,
88
+ },
89
+ },
90
+ thumbnail_config: {
91
+ bucket: nil,
92
+ storage_class: nil,
93
+ permissions:
94
+ {
95
+ grantee_type: nil,
96
+ grantee: nil,
97
+ access: nil,
98
+ },
99
+ },
100
+
101
+ },
102
+ :Jobs => {
103
+ # required
104
+ pipeline_id: nil,
105
+ # required
106
+ input: {
107
+ key: nil,
108
+ frame_rate: nil,
109
+ resolution: nil,
110
+ aspect_ratio: nil,
111
+ interlaced: nil,
112
+ container: nil,
113
+ },
114
+ output: {
115
+ key: nil,
116
+ thumbnail_pattern: nil,
117
+ rotate: nil,
118
+ preset_id: nil,
119
+ segment_duration: nil,
120
+ watermarks:
121
+ {
122
+ preset_watermark_id: nil,
123
+ input_key: nil,
124
+ },
125
+ album_art: {
126
+ merge_policy: nil,
127
+ artwork:
128
+ {
129
+ input_key: nil,
130
+ max_width: nil,
131
+ max_height: nil,
132
+ sizing_policy: nil,
133
+ padding_policy: nil,
134
+ album_art_format: nil,
135
+ },
136
+ },
137
+ composition:
138
+ {
139
+ time_span: {
140
+ start_time: nil,
141
+ duration: nil,
142
+ },
143
+ },
144
+ captions: {
145
+ merge_policy: nil,
146
+ caption_sources:
147
+ {
148
+ key: nil,
149
+ language: nil,
150
+ time_offset: nil,
151
+ label: nil,
152
+ },
153
+ caption_formats:
154
+ {
155
+ format: nil,
156
+ pattern: nil,
157
+ },
158
+ },
159
+ },
160
+ outputs:
161
+ {
162
+ key: nil,
163
+ thumbnail_pattern: nil,
164
+ rotate: nil,
165
+ preset_id: nil,
166
+ segment_duration: nil,
167
+ watermarks:
168
+ {
169
+ preset_watermark_id: nil,
170
+ input_key: nil,
171
+ },
172
+ album_art: {
173
+ merge_policy: nil,
174
+ artwork:
175
+ {
176
+ input_key: nil,
177
+ max_width: nil,
178
+ max_height: nil,
179
+ sizing_policy: nil,
180
+ padding_policy: nil,
181
+ album_art_format: nil,
182
+ },
183
+ },
184
+ composition:
185
+ {
186
+ time_span: {
187
+ start_time: nil,
188
+ duration: nil,
189
+ },
190
+ },
191
+ captions: {
192
+ merge_policy: nil,
193
+ caption_sources:
194
+ {
195
+ key: nil,
196
+ language: nil,
197
+ time_offset: nil,
198
+ label: nil,
199
+ },
200
+ caption_formats:
201
+ {
202
+ format: nil,
203
+ pattern: nil,
204
+ },
205
+ },
206
+ },
207
+ output_key_prefix: nil,
208
+ playlists:
209
+ {
210
+ name: nil,
211
+ format: nil,
212
+ output_keys: nil,
213
+ },
214
+
215
+ }
216
+ }
217
+ end
218
+
219
+ def connect()
220
+ begin
221
+ instprofcred = ::Aws::InstanceProfileCredentials.new( :ip_address => @options[:ip_address] || '169.254.169.254')
222
+ instprofcred.refresh!
223
+ major,minor,patch = ::Aws::VERSION.split(/\./)
224
+ if major.to_i >= 2 and minor.to_i > 0
225
+ raise 'Cannot obtain InstanceProfileCredentials' unless instprofcred.credentials.access_key_id
226
+ else
227
+ raise 'Cannot obtain InstanceProfileCredentials' unless instprofcred.access_key_id
228
+ end
229
+ @logger.info instprofcred.inspect
230
+ # noinspection RubyArgCount
231
+ @elastictranscoder = ::Aws::ElasticTranscoder::Client.new(credentials: instprofcred, region: @region, :retry_limit => 10)
232
+ rescue Exception => e
233
+ if e.class.to_s.match %r'^Errno'
234
+ abort! "#{e.message}: (InstanceProfileCredentials)?"
235
+ else
236
+ case e.class.to_s
237
+ when /URI::InvalidURIError/
238
+ abort! "#{e.message}: HINT: Is the AWS SDK credentials configured correctly?"
239
+ else
240
+ abort! "#{e.message}"
241
+ end
242
+ end
243
+ end
244
+ end
245
+
246
+ def get_item_data(item, section, params)
247
+ # noinspection RubyStringKeysInHashInspection
248
+ hash = case section
249
+ when /Pipelines/
250
+ {
251
+ 'Arn' => item[:arn],
252
+ 'Name' => item[:name],
253
+ 'PipelineId' => item[:id],
254
+ 'Status' => item[:status],
255
+ 'Role' => item[:role],
256
+ 'InputBucket' => item[:input_bucket],
257
+ 'OutputBucket' => item[:output_bucket],
258
+ }
259
+ when /Presets/
260
+ {
261
+ 'Arn' => item[:arn],
262
+ 'Name' => item[:name],
263
+ 'Description' => item[:description],
264
+ 'PresetId' => item[:id],
265
+ 'Container' => item[:container],
266
+ }
267
+ when /Jobs/
268
+ {
269
+ 'Arn' => item[:arn],
270
+ }
271
+ else
272
+ abort! "Unsupported resource type: #{section}"
273
+ end
274
+ data = {}
275
+ hash.each{ |k,v| data[k] = v unless v.nil? }
276
+ data
277
+ end
278
+
279
+ end
280
+ end
281
+ end
282
+ end