active_encode 1.2.0 → 1.2.2

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.
Files changed (141) hide show
  1. checksums.yaml +4 -4
  2. data/.circleci/config.yml +1 -0
  3. data/active_encode.gemspec +1 -2
  4. data/lib/active_encode/engine_adapters/pass_through_adapter.rb +28 -7
  5. data/lib/active_encode/version.rb +1 -1
  6. metadata +4 -274
  7. data/spec/controllers/encode_record_controller_spec.rb +0 -53
  8. data/spec/fixtures//"file_with_double_quote/".low.mp4 +0 -0
  9. data/spec/fixtures//"file_with_double_quote/".mp4 +0 -0
  10. data/spec/fixtures/'file_with_single_quote'.low.mp4 +0 -0
  11. data/spec/fixtures/'file_with_single_quote'.mp4 +0 -0
  12. data/spec/fixtures/@/341/213/210/341/213/263/341/214/205/341/210/205 /341/210/233/341/210/255 /341/211/242. /341/210/206/341/212/225 /341/214/250/341/210/255/341/210/265. /341/210/205 /341/212/240/341/211/265/341/210/213/341/210/260!@#$^^&$%&.low.mov +0 -0
  13. data/spec/fixtures/@/341/213/210/341/213/263/341/214/205/341/210/205 /341/210/233/341/210/255 /341/211/242. /341/210/206/341/212/225 /341/214/250/341/210/255/341/210/265. /341/210/205 /341/212/240/341/211/265/341/210/213/341/210/260!@#$^^&$%&.mov +0 -0
  14. data/spec/fixtures/Bars_512kb.mp4 +0 -0
  15. data/spec/fixtures/elastic_transcoder/input_completed.json +0 -1
  16. data/spec/fixtures/elastic_transcoder/input_generic.json +0 -1
  17. data/spec/fixtures/elastic_transcoder/input_progressing.json +0 -1
  18. data/spec/fixtures/elastic_transcoder/job_canceled.json +0 -1
  19. data/spec/fixtures/elastic_transcoder/job_completed.json +0 -1
  20. data/spec/fixtures/elastic_transcoder/job_created.json +0 -1
  21. data/spec/fixtures/elastic_transcoder/job_failed.json +0 -1
  22. data/spec/fixtures/elastic_transcoder/job_progressing.json +0 -1
  23. data/spec/fixtures/elastic_transcoder/output_canceled.json +0 -1
  24. data/spec/fixtures/elastic_transcoder/output_completed.json +0 -1
  25. data/spec/fixtures/elastic_transcoder/output_failed.json +0 -1
  26. data/spec/fixtures/elastic_transcoder/output_progressing.json +0 -1
  27. data/spec/fixtures/elastic_transcoder/output_submitted.json +0 -1
  28. data/spec/fixtures/ffmpeg/cancelled-id/cancelled +0 -0
  29. data/spec/fixtures/ffmpeg/cancelled-id/error.log +0 -0
  30. data/spec/fixtures/ffmpeg/cancelled-id/exit_status.code +0 -1
  31. data/spec/fixtures/ffmpeg/cancelled-id/input_metadata +0 -90
  32. data/spec/fixtures/ffmpeg/cancelled-id/pid +0 -1
  33. data/spec/fixtures/ffmpeg/cancelled-id/progress +0 -11
  34. data/spec/fixtures/ffmpeg/completed-id/error.log +0 -0
  35. data/spec/fixtures/ffmpeg/completed-id/exit_status.code +0 -1
  36. data/spec/fixtures/ffmpeg/completed-id/input_metadata +0 -102
  37. data/spec/fixtures/ffmpeg/completed-id/output_metadata-high +0 -90
  38. data/spec/fixtures/ffmpeg/completed-id/output_metadata-low +0 -90
  39. data/spec/fixtures/ffmpeg/completed-id/pid +0 -1
  40. data/spec/fixtures/ffmpeg/completed-id/progress +0 -11
  41. data/spec/fixtures/ffmpeg/completed-id/video-high.mp4 +0 -0
  42. data/spec/fixtures/ffmpeg/completed-id/video-low.mp4 +0 -0
  43. data/spec/fixtures/ffmpeg/completed-with-warnings-id/error.log +0 -3
  44. data/spec/fixtures/ffmpeg/completed-with-warnings-id/exit_status.code +0 -1
  45. data/spec/fixtures/ffmpeg/completed-with-warnings-id/input_metadata +0 -102
  46. data/spec/fixtures/ffmpeg/completed-with-warnings-id/output_metadata-high +0 -90
  47. data/spec/fixtures/ffmpeg/completed-with-warnings-id/output_metadata-low +0 -90
  48. data/spec/fixtures/ffmpeg/completed-with-warnings-id/pid +0 -1
  49. data/spec/fixtures/ffmpeg/completed-with-warnings-id/progress +0 -11
  50. data/spec/fixtures/ffmpeg/completed-with-warnings-id/video-high.mp4 +0 -0
  51. data/spec/fixtures/ffmpeg/completed-with-warnings-id/video-low.mp4 +0 -0
  52. data/spec/fixtures/ffmpeg/failed-id/error.log +0 -1
  53. data/spec/fixtures/ffmpeg/failed-id/exit_status.code +0 -1
  54. data/spec/fixtures/ffmpeg/failed-id/input_metadata +0 -90
  55. data/spec/fixtures/ffmpeg/failed-id/pid +0 -1
  56. data/spec/fixtures/ffmpeg/failed-id/progress +0 -11
  57. data/spec/fixtures/ffmpeg/incomplete-id/error.log +0 -0
  58. data/spec/fixtures/ffmpeg/incomplete-id/exit_status.code +0 -1
  59. data/spec/fixtures/ffmpeg/incomplete-id/input_metadata +0 -102
  60. data/spec/fixtures/ffmpeg/incomplete-id/output_metadata-high +0 -90
  61. data/spec/fixtures/ffmpeg/incomplete-id/output_metadata-low +0 -90
  62. data/spec/fixtures/ffmpeg/incomplete-id/pid +0 -1
  63. data/spec/fixtures/ffmpeg/incomplete-id/progress +0 -11
  64. data/spec/fixtures/ffmpeg/incomplete-id/video-high.mp4 +0 -0
  65. data/spec/fixtures/ffmpeg/incomplete-id/video-low.mp4 +0 -0
  66. data/spec/fixtures/ffmpeg/running-id/error.log +0 -0
  67. data/spec/fixtures/ffmpeg/running-id/input_metadata +0 -90
  68. data/spec/fixtures/ffmpeg/running-id/pid +0 -1
  69. data/spec/fixtures/ffmpeg/running-id/progress +0 -11
  70. data/spec/fixtures/file with space.low.mp4 +0 -0
  71. data/spec/fixtures/file with space.mp4 +0 -0
  72. data/spec/fixtures/file.with :=+%sp3c!l-ch4cts().mp4 +0 -0
  73. data/spec/fixtures/file.with...periods.mp4 +0 -0
  74. data/spec/fixtures/file_without_metadata.low.webm +0 -0
  75. data/spec/fixtures/file_without_metadata.mp4 +0 -0
  76. data/spec/fixtures/file_without_metadata.webm +0 -0
  77. data/spec/fixtures/fireworks.low.mp4 +0 -0
  78. data/spec/fixtures/fireworks.mp4 +0 -0
  79. data/spec/fixtures/matterhorn/cancelled_response.xml +0 -323
  80. data/spec/fixtures/matterhorn/completed_response.xml +0 -4
  81. data/spec/fixtures/matterhorn/create_response.xml +0 -300
  82. data/spec/fixtures/matterhorn/delete_track_response.xml +0 -2
  83. data/spec/fixtures/matterhorn/failed_response.xml +0 -4
  84. data/spec/fixtures/matterhorn/purged_response.xml +0 -342
  85. data/spec/fixtures/matterhorn/running_response.xml +0 -1
  86. data/spec/fixtures/matterhorn/stop_completed_response.xml +0 -228
  87. data/spec/fixtures/matterhorn/stop_running_response.xml +0 -339
  88. data/spec/fixtures/media_convert/endpoints.json +0 -1
  89. data/spec/fixtures/media_convert/job_canceled.json +0 -412
  90. data/spec/fixtures/media_convert/job_canceling.json +0 -1
  91. data/spec/fixtures/media_convert/job_completed.json +0 -359
  92. data/spec/fixtures/media_convert/job_completed_detail.json +0 -1
  93. data/spec/fixtures/media_convert/job_completed_detail_query.json +0 -1
  94. data/spec/fixtures/media_convert/job_completed_empty_detail.json +0 -1
  95. data/spec/fixtures/media_convert/job_created.json +0 -408
  96. data/spec/fixtures/media_convert/job_failed.json +0 -406
  97. data/spec/fixtures/media_convert/job_progressing.json +0 -414
  98. data/spec/fixtures/pass_through/cancelled-id/cancelled +0 -0
  99. data/spec/fixtures/pass_through/cancelled-id/input_metadata +0 -90
  100. data/spec/fixtures/pass_through/completed-id/completed +0 -0
  101. data/spec/fixtures/pass_through/completed-id/input_metadata +0 -102
  102. data/spec/fixtures/pass_through/completed-id/output_metadata-high +0 -90
  103. data/spec/fixtures/pass_through/completed-id/output_metadata-low +0 -90
  104. data/spec/fixtures/pass_through/completed-id/video-high.mp4 +0 -0
  105. data/spec/fixtures/pass_through/completed-id/video-low.mp4 +0 -0
  106. data/spec/fixtures/pass_through/failed-id/error.log +0 -1
  107. data/spec/fixtures/pass_through/failed-id/input_metadata +0 -90
  108. data/spec/fixtures/pass_through/running-id/input_metadata +0 -90
  109. data/spec/fixtures/zencoder/job_create.json +0 -1
  110. data/spec/fixtures/zencoder/job_details_cancelled.json +0 -1
  111. data/spec/fixtures/zencoder/job_details_completed.json +0 -1
  112. data/spec/fixtures/zencoder/job_details_create.json +0 -1
  113. data/spec/fixtures/zencoder/job_details_failed.json +0 -73
  114. data/spec/fixtures/zencoder/job_details_running.json +0 -1
  115. data/spec/fixtures/zencoder/job_progress_cancelled.json +0 -13
  116. data/spec/fixtures/zencoder/job_progress_completed.json +0 -13
  117. data/spec/fixtures/zencoder/job_progress_create.json +0 -1
  118. data/spec/fixtures/zencoder/job_progress_failed.json +0 -13
  119. data/spec/fixtures/zencoder/job_progress_running.json +0 -1
  120. data/spec/integration/elastic_transcoder_adapter_spec.rb +0 -218
  121. data/spec/integration/ffmpeg_adapter_spec.rb +0 -535
  122. data/spec/integration/matterhorn_adapter_spec.rb +0 -130
  123. data/spec/integration/media_convert_adapter_spec.rb +0 -321
  124. data/spec/integration/pass_through_adapter_spec.rb +0 -293
  125. data/spec/integration/zencoder_adapter_spec.rb +0 -391
  126. data/spec/rails_helper.rb +0 -25
  127. data/spec/routing/encode_record_controller_routing_spec.rb +0 -10
  128. data/spec/spec_helper.rb +0 -20
  129. data/spec/test_app_templates/lib/generators/test_app_generator.rb +0 -16
  130. data/spec/units/callbacks_spec.rb +0 -66
  131. data/spec/units/core_spec.rb +0 -160
  132. data/spec/units/engine_adapter_spec.rb +0 -67
  133. data/spec/units/file_locator_spec.rb +0 -129
  134. data/spec/units/filename_sanitizer_spec.rb +0 -20
  135. data/spec/units/global_id_spec.rb +0 -50
  136. data/spec/units/input_spec.rb +0 -40
  137. data/spec/units/output_spec.rb +0 -42
  138. data/spec/units/persistence_spec.rb +0 -61
  139. data/spec/units/polling_job_spec.rb +0 -87
  140. data/spec/units/polling_spec.rb +0 -23
  141. data/spec/units/status_spec.rb +0 -81
@@ -1,321 +0,0 @@
1
- # frozen_string_literal: true
2
- require 'spec_helper'
3
- require 'aws-sdk-cloudwatchevents'
4
- require 'aws-sdk-cloudwatchlogs'
5
- require 'aws-sdk-mediaconvert'
6
- require 'aws-sdk-s3'
7
- require 'json'
8
- require 'active_encode/spec/shared_specs'
9
- require 'active_support/json'
10
- require 'active_support/time'
11
-
12
- def with_json_parsing
13
- old_settings = { parse_json_times: ActiveSupport.parse_json_times, time_zone: Time.zone }
14
- ActiveSupport.parse_json_times = true
15
- Time.zone = 'America/Chicago'
16
- yield
17
- ensure
18
- ActiveSupport.parse_json_times = old_settings[:parse_json_times]
19
- Time.zone = old_settings[:time_zone]
20
- end
21
-
22
- def reconstitute_response(fixture_path)
23
- with_json_parsing do
24
- HashWithIndifferentAccess.new(ActiveSupport::JSON.decode(File.read(File.join("spec/fixtures", fixture_path))))
25
- end
26
- end
27
-
28
- describe ActiveEncode::EngineAdapters::MediaConvertAdapter do
29
- around do |example|
30
- # Setting this before each test works around a stubbing + memoization limitation
31
- ActiveEncode::Base.engine_adapter = :media_convert
32
- ActiveEncode::Base.engine_adapter.role = 'arn:aws:iam::123456789012:role/service-role/MediaConvert_Default_Role'
33
- ActiveEncode::Base.engine_adapter.output_bucket = 'output-bucket'
34
- example.run
35
- ActiveEncode::Base.engine_adapter = :test
36
- end
37
-
38
- let(:job_id) { "1625859001514-vvqfwj" }
39
- let(:mediaconvert) { Aws::MediaConvert::Client.new(stub_responses: true) }
40
- let(:cloudwatch_events) { Aws::CloudWatchEvents::Client.new(stub_responses: true) }
41
- let(:cloudwatch_logs) { Aws::CloudWatchLogs::Client.new(stub_responses: true) }
42
-
43
- let(:s3client) { Aws::S3::Client.new(stub_responses: true) }
44
-
45
- before do
46
- mediaconvert.stub_responses(:describe_endpoints, reconstitute_response("media_convert/endpoints.json"))
47
-
48
- allow(Aws::MediaConvert::Client).to receive(:new).and_return(mediaconvert)
49
- allow(Aws::CloudWatchEvents::Client).to receive(:new).and_return(cloudwatch_events)
50
- allow(Aws::CloudWatchLogs::Client).to receive(:new).and_return(cloudwatch_logs)
51
- allow(Aws::S3::Client).to receive(:new).and_return(s3client)
52
- end
53
-
54
- let(:created_job) do
55
- mediaconvert.stub_responses(:create_job, reconstitute_response("media_convert/job_created.json"))
56
-
57
- ActiveEncode::Base.create(
58
- "s3://input-bucket/test_files/source_file.mp4",
59
- output_prefix: "active-encode-test/output",
60
- outputs: [
61
- { preset: "System-Avc_16x9_1080p_29_97fps_8500kbps", modifier: "-1080" },
62
- { preset: "System-Avc_16x9_720p_29_97fps_5000kbps", modifier: "-720" },
63
- { preset: "System-Avc_16x9_540p_29_97fps_3500kbps", modifier: "-540" }
64
- ],
65
- use_original_url: true
66
- )
67
- end
68
-
69
- let(:running_job) do
70
- mediaconvert.stub_responses(:get_job, reconstitute_response("media_convert/job_progressing.json"))
71
- ActiveEncode::Base.find(job_id)
72
- end
73
-
74
- let(:canceled_job) do
75
- mediaconvert.stub_responses(:get_job, reconstitute_response("media_convert/job_canceled.json"))
76
- ActiveEncode::Base.find(job_id)
77
- end
78
-
79
- let(:cancelling_job) do
80
- mediaconvert.stub_responses(:cancel_job, reconstitute_response("media_convert/job_canceling.json"))
81
- mediaconvert.stub_responses(:get_job, reconstitute_response("media_convert/job_canceled.json"))
82
- ActiveEncode::Base.find(job_id)
83
- end
84
-
85
- let(:completed_job) do
86
- mediaconvert.stub_responses(:get_job, reconstitute_response("media_convert/job_completed.json"))
87
- cloudwatch_logs.stub_responses(:start_query, reconstitute_response("media_convert/job_completed_detail_query.json"))
88
- cloudwatch_logs.stub_responses(:get_query_results, reconstitute_response("media_convert/job_completed_detail.json"))
89
-
90
- ActiveEncode::Base.find(job_id)
91
- end
92
-
93
- let(:recent_completed_job_without_results) do
94
- job_response = reconstitute_response("media_convert/job_completed.json")
95
- job_response["job"]["timing"]["finish_time"] = 5.minutes.ago
96
- mediaconvert.stub_responses(:get_job, job_response)
97
- cloudwatch_logs.stub_responses(:start_query, reconstitute_response("media_convert/job_completed_detail_query.json"))
98
- cloudwatch_logs.stub_responses(:get_query_results, reconstitute_response("media_convert/job_completed_empty_detail.json"))
99
-
100
- ActiveEncode::Base.find(job_id)
101
- end
102
-
103
- let(:failed_job) do
104
- mediaconvert.stub_responses(:get_job, reconstitute_response("media_convert/job_failed.json"))
105
-
106
- ActiveEncode::Base.find(job_id)
107
- end
108
-
109
- let(:completed_output) do
110
- [
111
- { id: "1625859001514-vvqfwj-output-auto", url: "s3://output-bucket/active-encode-test/output.m3u8",
112
- label: "output.m3u8", audio_codec: "AAC", duration: 888_020, video_codec: "H_264" },
113
- { id: "1625859001514-vvqfwj-output-1080", url: "s3://output-bucket/active-encode-test/output-1080.m3u8",
114
- label: "output-1080.m3u8", audio_bitrate: 128_000, audio_codec: "AAC", duration: 888_020,
115
- video_bitrate: 8_500_000, height: 1080, width: 1920, video_codec: "H_264", frame_rate: 29.97 },
116
- { id: "1625859001514-vvqfwj-output-720", url: "s3://output-bucket/active-encode-test/output-720.m3u8",
117
- label: "output-720.m3u8", audio_bitrate: 96_000, audio_codec: "AAC", duration: 888_020,
118
- video_bitrate: 5_000_000, height: 720, width: 1280, video_codec: "H_264", frame_rate: 29.97 },
119
- { id: "1625859001514-vvqfwj-output-540", url: "s3://output-bucket/active-encode-test/output-540.m3u8",
120
- label: "output-540.m3u8", audio_bitrate: 96_000, audio_codec: "AAC", duration: 888_020,
121
- video_bitrate: 3_500_000, height: 540, width: 960, video_codec: "H_264", frame_rate: 29.97 }
122
- ]
123
- end
124
- let(:completed_tech_metadata) { {} }
125
- let(:failed_tech_metadata) { {} }
126
-
127
- it_behaves_like "an ActiveEncode::EngineAdapter"
128
-
129
- describe "output location specification" do
130
- let(:operations) { mediaconvert.api_requests(exclude_presign: true) }
131
- before do
132
- mediaconvert.stub_responses(:create_job, reconstitute_response("media_convert/job_created.json"))
133
- end
134
-
135
- it "can use output_bucket and output_prefix" do
136
- ActiveEncode::Base.create(
137
- "s3://input-bucket/test_files/source_file.mp4",
138
- output_prefix: "active-encode-test/output",
139
- outputs: [],
140
- use_original_url: true
141
- )
142
- create_job_operation = operations.find { |o| o[:operation_name] == :create_job }
143
- expect(create_job_operation).to be_present
144
-
145
- destination = create_job_operation.dig(:params, :settings, :output_groups, 0,
146
- :output_group_settings, :hls_group_settings, :destination)
147
-
148
- expect(destination).to eq("s3://output-bucket/active-encode-test/output")
149
- end
150
-
151
- it "can use destination arg" do
152
- ActiveEncode::Base.create(
153
- "s3://input-bucket/test_files/source_file.mp4",
154
- destination: "s3://alternate-output-bucket/my-path/output",
155
- outputs: [],
156
- use_original_url: true
157
- )
158
- create_job_operation = operations.find { |o| o[:operation_name] == :create_job }
159
- expect(create_job_operation).to be_present
160
-
161
- destination = create_job_operation.dig(:params, :settings, :output_groups, 0,
162
- :output_group_settings, :hls_group_settings, :destination)
163
-
164
- expect(destination).to eq("s3://alternate-output-bucket/my-path/output")
165
- end
166
- end
167
-
168
- describe "output_group_destination_settings" do
169
- let(:operations) { mediaconvert.api_requests(exclude_presign: true) }
170
- before do
171
- mediaconvert.stub_responses(:create_job, reconstitute_response("media_convert/job_created.json"))
172
- end
173
-
174
- it "are sent to MediaConvert" do
175
- ActiveEncode::Base.create(
176
- "s3://input-bucket/test_files/source_file.mp4",
177
- destination: "s3://alternate-output-bucket/my-path/output",
178
- outputs: [],
179
- use_original_url: true,
180
- output_group_destination_settings: {
181
- s3_settings: {
182
- access_control: {
183
- canned_acl: "PUBLIC_READ"
184
- }
185
- }
186
- }
187
- )
188
-
189
- create_job_operation = operations.find { |o| o[:operation_name] == :create_job }
190
- expect(create_job_operation).to be_present
191
-
192
- destination_settings = create_job_operation.dig(:params, :settings, :output_groups, 0,
193
- :output_group_settings, :hls_group_settings, :destination_settings)
194
- expect(destination_settings).to eq({ s3_settings: { access_control: { canned_acl: "PUBLIC_READ" } } })
195
- end
196
- end
197
-
198
- describe "queue" do
199
- let(:operations) { mediaconvert.api_requests(exclude_presign: true) }
200
-
201
- it "uses the default queue" do
202
- mediaconvert.stub_responses(:create_job, reconstitute_response("media_convert/job_created.json"))
203
- ActiveEncode::Base.create(
204
- "s3://input-bucket/test_files/source_file.mp4",
205
- output_prefix: "active-encode-test/output",
206
- outputs: [],
207
- use_original_url: true
208
- )
209
- expect(operations).to include(include(operation_name: :create_job, params: include(queue: 'Default')))
210
- end
211
-
212
- it "uses a specific queue" do
213
- mediaconvert.stub_responses(:create_job, reconstitute_response("media_convert/job_created.json"))
214
- ActiveEncode::Base.engine_adapter.queue = 'test-queue'
215
- ActiveEncode::Base.create(
216
- "s3://input-bucket/test_files/source_file.mp4",
217
- output_prefix: "active-encode-test/output",
218
- outputs: [],
219
- use_original_url: true
220
- )
221
- expect(operations).to include(include(operation_name: :create_job, params: include(queue: 'test-queue')))
222
- end
223
- end
224
-
225
- describe "output" do
226
- it "contains all expected outputs" do
227
- completed_output.each do |expected_output|
228
- found_output = completed_job.output.find { |output| output.id == expected_output[:id] }
229
- expected_output.each_pair do |key, value|
230
- expect(found_output.send(key)).to eq(value)
231
- end
232
- end
233
- end
234
-
235
- it "has no logging entries but finished within the last 10 minutes" do
236
- expect(recent_completed_job_without_results.state).to eq(:running)
237
- end
238
-
239
- it "finished more than 10 minutes ago but has no logging entries" do
240
- mediaconvert.stub_responses(:get_job, reconstitute_response("media_convert/job_completed.json"))
241
- cloudwatch_logs.stub_responses(:start_query, reconstitute_response("media_convert/job_completed_detail_query.json"))
242
- cloudwatch_logs.stub_responses(:get_query_results, reconstitute_response("media_convert/job_completed_empty_detail.json"))
243
-
244
- expect { ActiveEncode::Base.find(job_id) }.to raise_error do |error|
245
- expect(error).to be_a(ActiveEncode::EngineAdapters::MediaConvertAdapter::ResultsNotAvailable)
246
- expect(error.encode).to be_a(ActiveEncode::Base)
247
- expect(error.encode.state).to eq(:completed)
248
- end
249
- end
250
- end
251
-
252
- describe "direct_output_lookup" do
253
- before do
254
- ActiveEncode::Base.engine_adapter.direct_output_lookup = true
255
- end
256
-
257
- it "contains all expected outputs" do
258
- completed_output.each do |expected_output|
259
- found_output = completed_job.output.find { |output| output.id == expected_output[:id] }
260
- expected_output.each_pair do |key, value|
261
- expect(found_output.send(key)).to eq(value)
262
- end
263
- end
264
- end
265
-
266
- it "does not make cloudwatch queries" do
267
- expect(cloudwatch_logs).not_to receive(:start_query)
268
- expect(cloudwatch_logs).not_to receive(:get_query_results)
269
-
270
- completed_job
271
- end
272
- end
273
-
274
- describe "#s3_uri" do
275
- context "when filename has no special characters" do
276
- context "non-s3 file" do
277
- let(:input_url) { "spec/fixtures/fireworks.mp4" }
278
- let(:source_bucket) { "bucket1" }
279
-
280
- it "calls the #upload_to_s3 method" do
281
- allow(SecureRandom).to receive(:uuid).and_return("randomstring")
282
- expect(described_class.new.send(:s3_uri, input_url, { masterfile_bucket: source_bucket })).to eq "randomstring/fireworks.mp4"
283
- end
284
- end
285
- context "s3 file" do
286
- let(:input_url) { "s3://bucket1/file.mp4" }
287
- let(:source_bucket) { "bucket1" }
288
-
289
- it "calls the #check_s3_bucket method" do
290
- expect(described_class.new.send(:s3_uri, input_url, { masterfile_bucket: source_bucket })).to eq "file.mp4"
291
- end
292
- end
293
- end
294
- context "when filename has special characters" do
295
- context "non-s3 file" do
296
- let(:input) { ["'file_with_single_quote'.mp4", '"file_with_double_quote".mp4', "file with space.mp4", "file.with...periods.mp4", "file.with :=+%sp3c!l-ch4cts().mp4", '@ወዳጅህ ማር ቢ. ሆን ጨርስ. ህ አትላሰ!@#$^^&$%&.mov'] }
297
- let(:clean) { ["_file_with_single_quote_.mp4", "_file_with_double_quote_.mp4", "file_with_space.mp4", "filewithperiods.mp4", "filewith_____sp3c_l-ch4cts__.mp4", '__________________________________.mov'] }
298
- let(:source_bucket) { "bucket1" }
299
-
300
- it "calls the #upload_to_s3 method" do
301
- allow(SecureRandom).to receive(:uuid).and_return("randomstring")
302
- input.each_with_index do |url, index|
303
- expect(described_class.new.send(:s3_uri, "spec/fixtures/#{url}", { masterfile_bucket: source_bucket })).to eq "randomstring/#{clean[index]}"
304
- end
305
- end
306
- end
307
- context "s3 file" do
308
- let(:input_urls) { ["s3://bucket1/'file_with_single_quote'.mp4", 's3://bucket1/"file_with_double_quote".mp4', "s3://bucket1/file with space.mp4", "s3://bucket1/file.with...periods.mp4", "s3://bucket1/file.with :=+%sp3c!l-ch4cts().mp4", 's3://bucket1/@ወዳጅህ ማር ቢ. ሆን ጨርስ. ህ አትላሰ!@#$^^&$%&.mov'] }
309
- let(:clean) { ["_file_with_single_quote_.mp4", "_file_with_double_quote_.mp4", "file_with_space.mp4", "filewithperiods.mp4", "filewith_____sp3c_l-ch4cts__.mp4", '__________________________________.mov'] }
310
- let(:source_bucket) { "bucket2" }
311
-
312
- it "calls the #check_s3_bucket method" do
313
- allow(SecureRandom).to receive(:uuid).and_return("randomstring")
314
- input_urls.each_with_index do |url, index|
315
- expect(described_class.new.send(:s3_uri, url, { masterfile_bucket: source_bucket })).to eq "randomstring/#{clean[index]}"
316
- end
317
- end
318
- end
319
- end
320
- end
321
- end
@@ -1,293 +0,0 @@
1
- # frozen_string_literal: true
2
- require 'rails_helper'
3
- require 'active_encode/spec/shared_specs'
4
-
5
- describe ActiveEncode::EngineAdapters::PassThroughAdapter do
6
- around do |example|
7
- ActiveEncode::Base.engine_adapter = :pass_through
8
-
9
- Dir.mktmpdir do |dir|
10
- @dir = dir
11
- example.run
12
- Dir.foreach(dir) do |e|
13
- next if e == "." || e == ".."
14
- FileUtils.rm_rf(File.join(dir, e))
15
- end
16
- end
17
-
18
- ActiveEncode::Base.engine_adapter = :test
19
- end
20
-
21
- let!(:work_dir) { stub_const "ActiveEncode::EngineAdapters::PassThroughAdapter::WORK_DIR", @dir }
22
- let(:file) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'fireworks.mp4').to_s }
23
- let(:low_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'fireworks.low.mp4').to_s }
24
- let(:created_job) do
25
- ActiveEncode::Base.create(file, outputs: [{ label: 'low', url: low_derivative }])
26
- end
27
- let(:running_job) do
28
- created_job
29
- end
30
- let(:canceled_job) do
31
- find_encode 'cancelled-id'
32
- end
33
- let(:cancelling_job) do
34
- find_encode 'running-id'
35
- end
36
- let(:completed_job) { find_encode "completed-id" }
37
- let(:failed_job) { find_encode 'failed-id' }
38
- let(:completed_tech_metadata) do
39
- {
40
- audio_bitrate: 171_030,
41
- audio_codec: 'mp4a-40-2',
42
- duration: 6315.0,
43
- file_size: 199_160,
44
- frame_rate: 23.719,
45
- height: 110.0,
46
- id: "completed-id",
47
- url: "/home/pdinh/Downloads/videoshort.mp4",
48
- video_bitrate: 74_477,
49
- video_codec: 'avc1',
50
- width: 200.0
51
- }
52
- end
53
- let(:completed_output) { [{ id: "completed-id" }] }
54
- let(:failed_tech_metadata) { {} }
55
-
56
- it_behaves_like "an ActiveEncode::EngineAdapter"
57
-
58
- def find_encode(id)
59
- # Precreate ffmpeg output directory and files
60
- FileUtils.copy_entry "spec/fixtures/pass_through/#{id}", "#{work_dir}/#{id}"
61
-
62
- # Simulate that progress is modified later than other files
63
- sleep 0.1
64
- FileUtils.touch Dir.glob("#{work_dir}/#{id}/*.mp4")
65
- touch_fixture(id, "completed")
66
- touch_fixture(id, "cancelled")
67
- touch_fixture(id, "error.log")
68
-
69
- # Stub out system calls
70
- allow_any_instance_of(ActiveEncode::EngineAdapters::PassThroughAdapter).to receive(:`).and_return(1234)
71
-
72
- ActiveEncode::Base.find(id)
73
- end
74
-
75
- def touch_fixture(id, filename)
76
- FileUtils.touch("#{work_dir}/#{id}/#{filename}") if File.exist? "#{work_dir}/#{id}/#{filename}"
77
- end
78
-
79
- describe "#create" do
80
- subject { created_job }
81
-
82
- it "creates a directory whose name is the encode id" do
83
- expect(File).to exist("#{work_dir}/#{subject.id}")
84
- end
85
-
86
- context "input file exists" do
87
- it "has the input technical metadata in a file" do
88
- expect(File.read("#{work_dir}/#{subject.id}/input_metadata")).not_to be_empty
89
- end
90
- end
91
-
92
- context "input file doesn't exist" do
93
- let(:missing_file) { "file:///a_bogus_file.mp4" }
94
- let(:missing_job) { ActiveEncode::Base.create(missing_file, outputs: [{ label: "low", url: 'mp4' }]) }
95
-
96
- it "returns the encode with correct error" do
97
- expect(missing_job.errors).to include("#{missing_file} does not exist or is not accessible")
98
- expect(missing_job.percent_complete).to be 1
99
- end
100
- end
101
-
102
- context "input file is not media" do
103
- let(:nonmedia_file) { "file://" + Rails.root.join('Gemfile').to_s }
104
- let(:nonmedia_job) { ActiveEncode::Base.create(nonmedia_file, outputs: [{ label: "low", url: nonmedia_file }]) }
105
-
106
- it "returns the encode with correct error" do
107
- expect(nonmedia_job.errors).to include("Error inspecting input: #{nonmedia_file}")
108
- expect(nonmedia_job.percent_complete).to be 1
109
- end
110
- end
111
-
112
- context "input file format does not match extension" do
113
- let(:improper_format_file) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'file_without_metadata.mp4').to_s }
114
- let(:improper_format_job) { ActiveEncode::Base.create(improper_format_file, outputs: [{ label: "low", url: improper_format_file }]) }
115
-
116
- it "returns the encode with correct error" do
117
- expect(improper_format_job.errors).to include("Error inspecting input: #{improper_format_file}")
118
- expect(improper_format_job.percent_complete).to be 1
119
- end
120
- end
121
-
122
- context "input file without metadata" do
123
- let(:file_without_metadata) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'file_without_metadata.webm').to_s }
124
- let(:file_without_metadata_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'file_without_metadata.low.webm').to_s }
125
- let(:create_without_metadata_job) { ActiveEncode::Base.create(file_without_metadata, outputs: [{ label: "low", url: file_without_metadata_derivative }]) }
126
- let(:find_without_metadata_job) { ActiveEncode::Base.find create_without_metadata_job.id }
127
-
128
- it "does not have errors" do
129
- expect(find_without_metadata_job.errors).to be_empty
130
- end
131
-
132
- it "has the input technical metadata in a file" do
133
- expect(File.read("#{work_dir}/#{create_without_metadata_job.id}/input_metadata")).not_to be_empty
134
- end
135
-
136
- it "assigns the correct duration to the encode" do
137
- expect(create_without_metadata_job.input.duration).to eq 68_653
138
- expect(find_without_metadata_job.input.duration).to eq 68_653
139
- end
140
-
141
- context 'when uri encoded' do
142
- let(:file_without_metadata) { Addressable::URI.encode("file://" + Rails.root.join('..', 'spec', 'fixtures', 'file_without_metadata.webm').to_s) }
143
- let(:file_without_metadata_derivative) { Addressable::URI.encode("file://" + Rails.root.join('..', 'spec', 'fixtures', 'file_without_metadata.low.webm').to_s) }
144
-
145
- it "does not have errors" do
146
- expect(find_without_metadata_job.errors).to be_empty
147
- end
148
-
149
- it "has the input technical metadata in a file" do
150
- expect(File.read("#{work_dir}/#{create_without_metadata_job.id}/input_metadata")).not_to be_empty
151
- end
152
-
153
- it "assigns the correct duration to the encode" do
154
- expect(create_without_metadata_job.input.duration).to eq 68_653
155
- expect(find_without_metadata_job.input.duration).to eq 68_653
156
- end
157
- end
158
- end
159
-
160
- context "input filename with spaces" do
161
- let(:file_with_space) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'file with space.mp4').to_s }
162
- let(:file_with_space_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'file with space.low.mp4').to_s }
163
- let!(:create_space_job) { ActiveEncode::Base.create(file_with_space, outputs: [{ label: "low", url: file_with_space_derivative }]) }
164
- let(:find_space_job) { ActiveEncode::Base.find create_space_job.id }
165
-
166
- it "does not have errors" do
167
- expect(find_space_job.errors).to be_empty
168
- end
169
-
170
- it "has the input technical metadata in a file" do
171
- expect(File.read("#{work_dir}/#{create_space_job.id}/input_metadata")).not_to be_empty
172
- end
173
-
174
- context 'when uri encoded' do
175
- let(:file_with_space) { Addressable::URI.encode("file://" + Rails.root.join('..', 'spec', 'fixtures', 'file with space.mp4').to_s) }
176
- let(:file_with_space_derivative) { Addressable::URI.encode("file://" + Rails.root.join('..', 'spec', 'fixtures', 'file with space.low.mp4').to_s) }
177
-
178
- it "does not have errors" do
179
- expect(find_space_job.errors).to be_empty
180
- end
181
-
182
- it "has the input technical metadata in a file" do
183
- expect(File.read("#{work_dir}/#{create_space_job.id}/input_metadata")).not_to be_empty
184
- end
185
- end
186
- end
187
-
188
- context "input filename with single quotes" do
189
- let(:file_with_single_quote) { "file://" + Rails.root.join('..', 'spec', 'fixtures', "'file_with_single_quote'.mp4").to_s }
190
- let(:file_with_single_quote_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', "'file_with_single_quote'.low.mp4").to_s }
191
- let!(:create_single_quote_job) { ActiveEncode::Base.create(file_with_single_quote, outputs: [{ label: "low", url: file_with_single_quote_derivative }]) }
192
- let(:find_single_quote_job) { ActiveEncode::Base.find create_single_quote_job.id }
193
-
194
- it "does not have errors" do
195
- expect(find_single_quote_job.errors).to be_empty
196
- end
197
-
198
- it "has the input technical metadata in a file" do
199
- expect(File.read("#{work_dir}/#{create_single_quote_job.id}/input_metadata")).not_to be_empty
200
- end
201
-
202
- context 'when uri encoded' do
203
- let(:file_with_single_quote) { Addressable::URI.encode("file://" + Rails.root.join('..', 'spec', 'fixtures', "'file_with_single_quote'.mp4").to_s) }
204
- let(:file_with_single_quote_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', "'file_with_single_quote'.low.mp4").to_s }
205
-
206
- it "does not have errors" do
207
- expect(find_single_quote_job.errors).to be_empty
208
- end
209
-
210
- it "has the input technical metadata in a file" do
211
- expect(File.read("#{work_dir}/#{create_single_quote_job.id}/input_metadata")).not_to be_empty
212
- end
213
- end
214
- end
215
-
216
- context "input filename with double quotes" do
217
- let(:file_with_double_quote) { "file://" + Rails.root.join('..', 'spec', 'fixtures', '"file_with_double_quote".mp4').to_s }
218
- let(:file_with_double_quote_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', '"file_with_double_quote".mp4').to_s }
219
- let!(:create_double_quote_job) { ActiveEncode::Base.create(file_with_double_quote, outputs: [{ label: "low", url: file_with_double_quote_derivative }]) }
220
- let(:find_double_quote_job) { ActiveEncode::Base.find create_double_quote_job.id }
221
-
222
- it "does not have errors" do
223
- expect(find_double_quote_job.errors).to be_empty
224
- end
225
-
226
- it "has the input technical metadata in a file" do
227
- expect(File.read("#{work_dir}/#{create_double_quote_job.id}/input_metadata")).not_to be_empty
228
- end
229
-
230
- context 'when uri encoded' do
231
- let(:file_with_double_quote) { Addressable::URI.encode("file://" + Rails.root.join('..', 'spec', 'fixtures', '"file_with_double_quote".mp4').to_s) }
232
- let(:file_with_double_quote_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', '"file_with_double_quote".mp4').to_s }
233
-
234
- it "does not have errors" do
235
- expect(find_double_quote_job.errors).to be_empty
236
- end
237
-
238
- it "has the input technical metadata in a file" do
239
- expect(File.read("#{work_dir}/#{create_double_quote_job.id}/input_metadata")).not_to be_empty
240
- end
241
- end
242
- end
243
-
244
- context "input filename with other special characters" do
245
- let(:file_with_special_characters) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'file.with :=+%sp3c!l-ch4cts().mp4').to_s }
246
- let(:file_with_special_characters_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'file.with :=+%sp3c!l-ch4cts().mp4').to_s }
247
- let!(:create_special_characters_job) { ActiveEncode::Base.create(file_with_special_characters, outputs: [{ label: "low", url: file_with_special_characters_derivative }]) }
248
- let(:find_special_characters_job) { ActiveEncode::Base.find create_special_characters_job.id }
249
- let(:file_with_more_special_characters) { "file://" + Rails.root.join('..', 'spec', 'fixtures', '@ወዳጅህ ማር ቢ. ሆን ጨርስ. ህ አትላሰ!@#$^^&$%&.mov').to_s }
250
- let(:file_with_more_special_characters_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', '@ወዳጅህ ማር ቢ. ሆን ጨርስ. ህ አትላሰ!@#$^^&$%&.mov').to_s }
251
- let!(:create_more_special_characters_job) { ActiveEncode::Base.create(file_with_more_special_characters, outputs: [{ label: "low", url: file_with_more_special_characters_derivative }]) }
252
- let(:find_more_special_characters_job) { ActiveEncode::Base.find create_more_special_characters_job.id }
253
-
254
- it "does not have errors" do
255
- expect(find_special_characters_job.errors).to be_empty
256
- expect(find_more_special_characters_job.errors).to be_empty
257
- end
258
-
259
- it "has the input technical metadata in a file" do
260
- expect(File.read("#{work_dir}/#{create_special_characters_job.id}/input_metadata")).not_to be_empty
261
- expect(File.read("#{work_dir}/#{create_more_special_characters_job.id}/input_metadata")).not_to be_empty
262
- end
263
-
264
- context 'when uri encoded' do
265
- let(:file_with_special_characters) { Addressable::URI.encode("file://" + Rails.root.join('..', 'spec', 'fixtures', 'file.with :=+%sp3c!l-ch4cts().mp4').to_s) }
266
- let(:file_with_special_characters_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', 'file.with :=+%sp3c!l-ch4cts().mp4').to_s }
267
- let(:file_with_more_special_characters) { Addressable::URI.encode("file://" + Rails.root.join('..', 'spec', 'fixtures', '@ወዳጅህ ማር ቢ. ሆን ጨርስ. ህ አትላሰ!@#$^^&$%&.mov').to_s) }
268
- let(:file_with_more_special_characters_derivative) { "file://" + Rails.root.join('..', 'spec', 'fixtures', '@ወዳጅህ ማር ቢ. ሆን ጨርስ. ህ አትላሰ!@#$^^&$%&.mov').to_s }
269
-
270
- it "does not have errors" do
271
- expect(find_special_characters_job.errors).to be_empty
272
- expect(find_more_special_characters_job.errors).to be_empty
273
- end
274
-
275
- it "has the input technical metadata in a file" do
276
- expect(File.read("#{work_dir}/#{create_special_characters_job.id}/input_metadata")).not_to be_empty
277
- expect(File.read("#{work_dir}/#{create_more_special_characters_job.id}/input_metadata")).not_to be_empty
278
- end
279
- end
280
- end
281
-
282
- context 'when failed' do
283
- subject { created_job }
284
-
285
- before do
286
- allow_any_instance_of(Object).to receive(:`).and_raise Errno::ENOENT
287
- end
288
-
289
- it { is_expected.to be_failed }
290
- it { expect(subject.errors).to be_present }
291
- end
292
- end
293
- end