alephant-broker 3.10.2 → 3.11.0

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: 223acfc17ab349160c5dbf9597213a35b9cdc33a
4
- data.tar.gz: abb1103b13b95e494096b531ad8c109d2c965bdc
3
+ metadata.gz: 58251bb948e3620c95b0c67e8643e60426c25818
4
+ data.tar.gz: c355b17fe2d366043fbd84f5e284377f9d353a44
5
5
  SHA512:
6
- metadata.gz: ec8f97f5911fef1ca5d4bfee7694fee0c9173d4c2275dec58ae3d2161b0d6b19ccf6faee403d00beaa54c7bcaec8dcbeaa80a584d0f45da1e05e0277a6856d28
7
- data.tar.gz: 89841c9e7fa8bcc92e2d20da30834e0b63d80f8cca322a0e65b1ad0455390dba3161a61d5ac03ab7d585968b5b693f34ac1be6d3294cfa135359f968be608867
6
+ metadata.gz: dbdaf0f97e7c873b030be8418d6b7b7a076826fcd576d7f60b9c5f734f4ac8a13db6af1cb4744b222b48ee01abd267c6df051f22fac85dd8285b53b36128ce2c
7
+ data.tar.gz: a143fb0fbca1a39ab62a1a7facd718f9f38221a53daae7514ca82d1f9b7a42b3992ba06f8b427da717a919a50801f9877bb56d7c4b34e7adeae69702c5d63fde
@@ -38,4 +38,5 @@ Gem::Specification.new do |spec|
38
38
  spec.add_runtime_dependency "dalli-elasticache"
39
39
  spec.add_runtime_dependency "faraday"
40
40
  spec.add_runtime_dependency "crimp"
41
+ spec.add_runtime_dependency "listen", "~> 3.0.0"
41
42
  end
@@ -13,23 +13,23 @@ module Alephant
13
13
  end
14
14
 
15
15
  def method
16
- settings['REQUEST_METHOD']
16
+ settings["REQUEST_METHOD"]
17
17
  end
18
18
 
19
19
  def post?
20
- settings['REQUEST_METHOD'] == 'POST'
20
+ settings["REQUEST_METHOD"] == "POST"
21
21
  end
22
22
 
23
23
  def get?
24
- settings['REQUEST_METHOD'] == 'GET'
24
+ settings["REQUEST_METHOD"] == "GET"
25
25
  end
26
26
 
27
27
  def query
28
- settings['QUERY_STRING'] || ""
28
+ settings["QUERY_STRING"] || ""
29
29
  end
30
30
 
31
31
  def path
32
- settings['PATH_INFO']
32
+ settings["PATH_INFO"]
33
33
  end
34
34
 
35
35
  def if_none_match
@@ -51,7 +51,7 @@ module Alephant
51
51
  private
52
52
 
53
53
  def rack_input
54
- (settings['rack.input'].read).tap { settings['rack.input'].rewind }
54
+ (settings["rack.input"].read).tap { settings["rack.input"].rewind }
55
55
  end
56
56
 
57
57
  def parse(json)
@@ -10,24 +10,37 @@ module Alephant
10
10
  attr_reader :batch_id, :components, :load_strategy
11
11
 
12
12
  def initialize(component_factory, env)
13
- logger.info "Request::Batch#initialize: id: #{env.data['batch_id']}" if env.data
13
+ if env.data
14
+ @batch_id = env.data["batch_id"]
15
+ else
16
+ @batch_id = env.options.fetch("batch_id", nil)
17
+ end
18
+
19
+ logger.info "Request::Batch#initialize: id: #{batch_id}"
14
20
 
15
- @batch_id = env.data["batch_id"] if env.data
16
21
  @component_factory = component_factory
17
- @components = components_for env
22
+
23
+ @components = env.post? ? components_post(env) : components_get(env)
18
24
  end
19
25
 
20
26
  private
21
27
 
22
- def components_for(env)
28
+ def components_post(env)
23
29
  ((env.data || {}).fetch("components", []) || []).map do |c|
24
- @component_factory.create(
25
- c["component"],
26
- batch_id,
27
- c["options"]
28
- )
30
+ create_component(c["component"], batch_id, c["options"])
31
+ end
32
+ end
33
+
34
+ def components_get(env)
35
+ (env.options.fetch("components", []) || []).map do |c|
36
+ options = c[1].fetch("options", {}) || {}
37
+ create_component(c[1]["component"], batch_id, options)
29
38
  end
30
39
  end
40
+
41
+ def create_component(component, batch_id, options)
42
+ @component_factory.create(component, batch_id, options)
43
+ end
31
44
  end
32
45
  end
33
46
  end
@@ -6,18 +6,18 @@ module Alephant
6
6
  module Request
7
7
  class Factory
8
8
  def self.request_type_from(env)
9
- env.path.split('/')[1]
9
+ env.path.split("/")[1]
10
10
  end
11
11
 
12
12
  def self.request_for(load_strategy, env)
13
13
  component_factory = ComponentFactory.new load_strategy
14
14
 
15
15
  case request_type_from(env)
16
- when 'component'
16
+ when "component"
17
17
  Asset.new(component_factory, env)
18
- when 'components'
18
+ when "components"
19
19
  Batch.new(component_factory, env)
20
- when 'status'
20
+ when "status"
21
21
  Status.new
22
22
  else
23
23
  NotFound.new
@@ -12,7 +12,7 @@ module Alephant
12
12
 
13
13
  attr_reader :content, :headers, :status
14
14
 
15
- NOT_MODIFIED_STATUS_CODE = 202
15
+ NOT_MODIFIED_STATUS_CODE = 304
16
16
 
17
17
  STATUS_CODE_MAPPING = {
18
18
  200 => "ok",
@@ -62,6 +62,7 @@ module Alephant
62
62
  end
63
63
 
64
64
  def self.component_not_modified(headers, request_env)
65
+ return false if request_env.post?
65
66
  return false if request_env.if_modified_since.nil? && request_env.if_none_match.nil?
66
67
 
67
68
  last_modified_match = !request_env.if_modified_since.nil? && headers["Last-Modified"] == request_env.if_modified_since
@@ -1,5 +1,5 @@
1
1
  module Alephant
2
2
  module Broker
3
- VERSION = "3.10.2"
3
+ VERSION = "3.11.0"
4
4
  end
5
5
  end
@@ -117,7 +117,7 @@ describe Alephant::Broker::Application do
117
117
  specify { expect(last_response.headers["Last-Modified"]).to eq("Mon, 11 Apr 2016 10:39:57 GMT") }
118
118
  end
119
119
 
120
- describe "Components endpoint '/components'" do
120
+ describe "Components endpoint '/components' POST" do
121
121
  let(:fixture_path) { "#{File.dirname(__FILE__)}/../fixtures/json" }
122
122
  let(:batch_json) do
123
123
  IO.read("#{fixture_path}/batch.json").strip
@@ -169,7 +169,7 @@ describe Alephant::Broker::Application do
169
169
  end
170
170
  end
171
171
 
172
- describe "Components unmodified '/components' response" do
172
+ describe "Components POST unmodified '/components' response" do
173
173
  let(:fixture_path) { "#{File.dirname(__FILE__)}/../fixtures/json" }
174
174
  let(:batch_json) { IO.read("#{fixture_path}/batch.json").strip }
175
175
  let(:batch_compiled_json) { IO.read("#{fixture_path}/batch_compiled.json").strip }
@@ -216,8 +216,8 @@ describe Alephant::Broker::Application do
216
216
  "HTTP_IF_NONE_MATCH" => etag)
217
217
  end
218
218
 
219
- specify { expect(last_response.status).to eql not_modified_status_code }
220
- specify { expect(last_response.body).to eq "" }
219
+ specify { expect(last_response.status).to eql 200 }
220
+ specify { expect(last_response.body).to eq batch_compiled_json }
221
221
 
222
222
  describe "response should have headers" do
223
223
  it "should have a Content-Type header" do
@@ -241,6 +241,131 @@ describe Alephant::Broker::Application do
241
241
  end
242
242
  end
243
243
 
244
+ describe "Components endpoint '/components' GET" do
245
+ let(:fixture_path) { "#{File.dirname(__FILE__)}/../fixtures/json" }
246
+ let(:batch_compiled_json) do
247
+ IO.read("#{fixture_path}/batch_compiled.json").strip
248
+ end
249
+ let(:s3_double_batch) { instance_double("Alephant::Storage") }
250
+
251
+ before do
252
+ allow(s3_double_batch).to receive(:get).and_return(
253
+ content,
254
+ AWS::Core::Data.new(
255
+ :content_type => "test/content",
256
+ :content => "Test",
257
+ :meta => {
258
+ :head_ETag => "\"abc\"",
259
+ :"head_Last-Modified" => "Mon, 11 Apr 2016 09:39:57 GMT"
260
+ }
261
+ )
262
+ )
263
+
264
+ allow(Alephant::Storage).to receive(:new) { s3_double_batch }
265
+ end
266
+
267
+ context "when using valid batch asset data" do
268
+ let(:path) { "/components/batch?batch_id=baz&components[ni_council_results_table][component]=ni_council_results_table&components[ni_council_results_table][options][foo]=bar&components[ni_council_results_table_no_options][component]=ni_council_results_table" }
269
+ let(:content_type) { "application/json" }
270
+
271
+ before { get path, {}, "CONTENT_TYPE" => content_type }
272
+
273
+ specify { expect(last_response.status).to eql 200 }
274
+ specify { expect(last_response.body).to eq batch_compiled_json }
275
+
276
+ describe "response should have headers" do
277
+ it "should have content headers" do
278
+ expect(last_response.headers["Content-Type"]).to eq("application/json")
279
+ expect(last_response.headers["Content-Length"]).to eq("266")
280
+ end
281
+
282
+ it "should have ETag cache header" do
283
+ expect(last_response.headers["ETag"]).to eq('"34774567db979628363e6e865127623f"')
284
+ end
285
+
286
+ it "should have most recent Last-Modified header" do
287
+ expect(last_response.headers["Last-Modified"]).to eq("Mon, 11 Apr 2016 10:39:57 GMT")
288
+ end
289
+ end
290
+ end
291
+ end
292
+
293
+ describe "Components GET unmodified '/components' response" do
294
+ let(:fixture_path) { "#{File.dirname(__FILE__)}/../fixtures/json" }
295
+ let(:batch_compiled_json) { IO.read("#{fixture_path}/batch_compiled.json").strip }
296
+ let(:s3_double_with_etag) { instance_double("Alephant::Storage") }
297
+ let(:lookup_location_double_for_options_request) do
298
+ instance_double("Alephant::Lookup::Location", :location => "test/location/with/options")
299
+ end
300
+
301
+ before do
302
+ allow(lookup_helper_double).to receive(:read)
303
+ .with("ni_council_results_table", { :foo => "bar" }, "111")
304
+ .and_return(lookup_location_double_for_options_request)
305
+
306
+ allow(s3_double_with_etag).to receive(:get)
307
+ .with("test/location")
308
+ .and_return(
309
+ content
310
+ )
311
+
312
+ allow(s3_double_with_etag).to receive(:get)
313
+ .with("test/location/with/options")
314
+ .and_return(
315
+ AWS::Core::Data.new(
316
+ :content_type => "test/content",
317
+ :content => "Test",
318
+ :meta => {
319
+ "head_ETag" => "abc",
320
+ "head_Last-Modified" => "Mon, 11 Apr 2016 09:39:57 GMT"
321
+ }
322
+ )
323
+ )
324
+
325
+ allow(Alephant::Storage).to receive(:new) { s3_double_with_etag }
326
+ end
327
+
328
+ context "when requesting an unmodified response with GET" do
329
+ let(:path) { "/components/batch?batch_id=baz&components[ni_council_results_table][component]=ni_council_results_table&components[ni_council_results_table][options][foo]=bar&components[ni_council_results_table_no_options][component]=ni_council_results_table" }
330
+ let(:content_type) { "application/json" }
331
+ let(:etag) { '"34774567db979628363e6e865127623f"' }
332
+
333
+ before do
334
+ get(
335
+ path,
336
+ {},
337
+ {
338
+ "CONTENT_TYPE" => content_type,
339
+ "HTTP_IF_NONE_MATCH" => etag
340
+ }
341
+ )
342
+ end
343
+
344
+ specify { expect(last_response.status).to eql not_modified_status_code }
345
+ specify { expect(last_response.body).to eq "" }
346
+
347
+ describe "response should have headers" do
348
+ it "should not have a Content-Type header" do
349
+ expect(last_response.headers).to_not include("Content-Type")
350
+ end
351
+
352
+ it "should have ETag cache header" do
353
+ expect(last_response.headers["ETag"]).to eq(etag)
354
+ end
355
+
356
+ it "should have most recent Last-Modified header" do
357
+ expect(last_response.headers["Last-Modified"]).to eq("Mon, 11 Apr 2016 10:39:57 GMT")
358
+ end
359
+
360
+ it "shoud not have no cache headers" do
361
+ expect(last_response.headers).to_not include("Cache-Control")
362
+ expect(last_response.headers).to_not include("Pragma")
363
+ expect(last_response.headers).to_not include("Expires")
364
+ end
365
+ end
366
+ end
367
+ end
368
+
244
369
  describe "S3 headers" do
245
370
  let(:content) do
246
371
  AWS::Core::Data.new(
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: alephant-broker
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.10.2
4
+ version: 3.11.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - BBC News
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-04-22 00:00:00.000000000 Z
11
+ date: 2016-04-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  requirement: !ruby/object:Gem::Requirement
@@ -262,6 +262,20 @@ dependencies:
262
262
  - - '>='
263
263
  - !ruby/object:Gem::Version
264
264
  version: '0'
265
+ - !ruby/object:Gem::Dependency
266
+ requirement: !ruby/object:Gem::Requirement
267
+ requirements:
268
+ - - ~>
269
+ - !ruby/object:Gem::Version
270
+ version: 3.0.0
271
+ name: listen
272
+ prerelease: false
273
+ type: :runtime
274
+ version_requirements: !ruby/object:Gem::Requirement
275
+ requirements:
276
+ - - ~>
277
+ - !ruby/object:Gem::Version
278
+ version: 3.0.0
265
279
  description: Brokers requests for alephant components
266
280
  email:
267
281
  - FutureMediaNewsRubyGems@bbc.co.uk