gds-api-adapters 19.2.0 → 20.0.0

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 2d7a14cdb0314fd0e249e1d7a958e436a9423a0a
4
- data.tar.gz: 6c964b35d713dd3ffb6de9d2c4e4ec680ce84e2f
3
+ metadata.gz: 87f540ebb20c9b25a5f646a9fe87417175da9a69
4
+ data.tar.gz: 1d93e60b2b6a442d30b82b8b587fadfff26c85b3
5
5
  SHA512:
6
- metadata.gz: aa837106a456ce8863e297588642e1b16caf416da36cbdff0d80fce1e30922450cb49260eee9d6bb18ca889546d2566da40594232dfe1e012b5f6a3b7a7c7fcf
7
- data.tar.gz: b42cbd5d65b6243174c9804fc9f3d676ca7a518a4430b0c574b3417d27420f58b9af8a1b902b0954f623bf6ce6bd01fe908295f263abff9e4d5ea06aafb9f93b
6
+ metadata.gz: f4b493b63635ccaac3987a6481699af88a63d95e55b42479d73b75bacda3c486f41d9bd7cded4783b59eb63239c02e9c5e3e867781dd6e99ba995e5c5b9dc254
7
+ data.tar.gz: a1416aa6e547c77cf7a5469494b00766878eec0d41f1038130b1f638d37c84b66ec9c4545fa969d831c64646b260754a74cc08ce692d738c2002b63f132213be
@@ -24,10 +24,6 @@ module GdsApi
24
24
  @business_support_api ||= GdsApi::BusinessSupportApi.new(Plek.current.find("business-support-api"), options)
25
25
  end
26
26
 
27
- def collections_api(options = {})
28
- @collections_api ||= GdsApi::CollectionsApi.new(Plek.current.find("collections-api"), options)
29
- end
30
-
31
27
  def content_api(options = {})
32
28
  @content_api ||= GdsApi::ContentApi.new(Plek.current.find("contentapi"), options)
33
29
  end
@@ -212,23 +212,14 @@ module GdsApi
212
212
  # or nil if no cache information is provided
213
213
  def response_cache_time(response)
214
214
  if response.headers[:cache_control]
215
- # The Cache-control header is composed of a comma-separated string
216
- # so split this apart before we look for particular values
217
- cache_parts = response.headers[:cache_control].split(',').map(&:strip)
218
-
219
- # If no-cache is present, this takes precedent over any other value
220
- # in this header
221
- return Time.now.utc if cache_parts.include?("no-cache")
222
-
223
- # Otherwise, look for a 'max-age=123' value, which is the number of
224
- # seconds for which to cache the response.
225
- max_age = cache_parts.map {|x| x.match(/max-age=(\d+)/) }.compact.first
226
- if max_age
227
- return Time.now.utc + max_age[1].to_i
228
- end
229
- end
215
+ cache_control = Rack::Cache::CacheControl.new(response.headers[:cache_control])
230
216
 
231
- if response.headers[:expires]
217
+ if cache_control.private? || cache_control.no_cache? || cache_control.no_store?
218
+ Time.now.utc
219
+ elsif cache_control.max_age
220
+ Time.now.utc + cache_control.max_age
221
+ end
222
+ elsif response.headers[:expires]
232
223
  Time.httpdate response.headers[:expires]
233
224
  end
234
225
  end
@@ -46,24 +46,28 @@ module GdsApi
46
46
  end
47
47
 
48
48
  def expires_at
49
- if headers[:date] && cache_control_headers = headers[:cache_control]
50
- max_age = Rack::Cache::CacheControl.new(cache_control_headers)['max-age']
49
+ if headers[:date] && cache_control.max_age
51
50
  response_date = Time.parse(headers[:date])
52
-
53
- return response_date + max_age.to_i if max_age
51
+ response_date + cache_control.max_age
52
+ elsif headers[:expires]
53
+ Time.parse(headers[:expires])
54
54
  end
55
- Time.parse(headers[:expires]) if headers[:expires]
56
55
  end
57
56
 
58
57
  def expires_in
59
58
  return unless headers[:date]
60
59
 
61
- max_age = Rack::Cache::CacheControl.new(headers[:cache_control])['max-age'] if headers[:cache_control]
62
- max_age ||= Time.parse(headers[:expires]) - Time.parse(headers[:date]) if headers[:expires]
63
- return unless max_age
64
-
65
60
  age = Time.now.utc - Time.parse(headers[:date])
66
- max_age.to_i - age.to_i
61
+
62
+ if cache_control.max_age
63
+ cache_control.max_age - age.to_i
64
+ elsif headers[:expires]
65
+ Time.parse(headers[:expires]).to_i - Time.now.utc.to_i
66
+ end
67
+ end
68
+
69
+ def cache_control
70
+ @cache_control ||= Rack::Cache::CacheControl.new(headers[:cache_control])
67
71
  end
68
72
 
69
73
  def to_hash
@@ -9,10 +9,26 @@ module GdsApi
9
9
 
10
10
  CONTENT_STORE_ENDPOINT = Plek.current.find('content-store')
11
11
 
12
- def content_store_has_item(base_path, body = content_item_for_base_path(base_path), expires_in = 900)
12
+ # Stubs a content item in the content store.
13
+ # The following options can be passed in:
14
+ #
15
+ # :max_age will set the max-age of the Cache-Control header in the response. Defaults to 900
16
+ # :private if true, the Cache-Control header will include the "private" directive. By default it
17
+ # will include "public"
18
+ def content_store_has_item(base_path, body = content_item_for_base_path(base_path), options = {})
19
+ max_age = options.fetch(:max_age, 900)
20
+ visibility = options[:private] ? "private" : "public"
13
21
  url = CONTENT_STORE_ENDPOINT + "/content" + base_path
14
22
  body = body.to_json unless body.is_a?(String)
15
- stub_request(:get, url).to_return(status: 200, body: body, headers: {cache_control: "public, max-age=#{expires_in}", date: Time.now.httpdate})
23
+
24
+ stub_request(:get, url).to_return(
25
+ status: 200,
26
+ body: body,
27
+ headers: {
28
+ cache_control: "#{visibility}, max-age=#{max_age}",
29
+ date: Time.now.httpdate
30
+ }
31
+ )
16
32
  end
17
33
 
18
34
  def content_store_does_not_have_item(base_path)
@@ -1,3 +1,3 @@
1
1
  module GdsApi
2
- VERSION = '19.2.0'
2
+ VERSION = '20.0.0'
3
3
  end
@@ -247,6 +247,44 @@ class JsonClientTest < MiniTest::Spec
247
247
  end
248
248
  end
249
249
 
250
+ def test_does_not_cache_responses_with_cache_control_private
251
+ url = "http://some.endpoint/private.json"
252
+ result = {"foo" => "bar"}
253
+ stub_request(:get, url).to_return(
254
+ :body => JSON.dump(result),
255
+ :status => 200,
256
+ :headers => { "Cache-Control" => "max-age=600, private" }
257
+ )
258
+
259
+ response_a = GdsApi::JsonClient.new.get_json(url)
260
+
261
+ Timecop.travel( 7 * 60 - 30) do # now + 6 mins 30 secs
262
+ response_b = GdsApi::JsonClient.new.get_json(url)
263
+
264
+ assert_requested :get, url, times: 2
265
+ assert_equal response_a.to_hash, response_b.to_hash
266
+ end
267
+ end
268
+
269
+ def test_does_not_cache_responses_with_cache_control_no_store
270
+ url = "http://some.endpoint/private.json"
271
+ result = {"foo" => "bar"}
272
+ stub_request(:get, url).to_return(
273
+ :body => JSON.dump(result),
274
+ :status => 200,
275
+ :headers => { "Cache-Control" => "max-age=600, no-store" }
276
+ )
277
+
278
+ response_a = GdsApi::JsonClient.new.get_json(url)
279
+
280
+ Timecop.travel( 7 * 60 - 30) do # now + 6 mins 30 secs
281
+ response_b = GdsApi::JsonClient.new.get_json(url)
282
+
283
+ assert_requested :get, url, times: 2
284
+ assert_equal response_a.to_hash, response_b.to_hash
285
+ end
286
+ end
287
+
250
288
  def test_should_respect_cache_control_headers_with_no_cache_and_max_age
251
289
  url = "http://some.endpoint/no_cache_and_max_age.json"
252
290
  result = {"foo" => "bar"}
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gds-api-adapters
3
3
  version: !ruby/object:Gem::Version
4
- version: 19.2.0
4
+ version: 20.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - James Stewart
@@ -275,7 +275,6 @@ files:
275
275
  - lib/gds_api/asset_manager.rb
276
276
  - lib/gds_api/base.rb
277
277
  - lib/gds_api/business_support_api.rb
278
- - lib/gds_api/collections_api.rb
279
278
  - lib/gds_api/content_api.rb
280
279
  - lib/gds_api/content_register.rb
281
280
  - lib/gds_api/content_store.rb
@@ -315,7 +314,6 @@ files:
315
314
  - lib/gds_api/test_helpers/asset_manager.rb
316
315
  - lib/gds_api/test_helpers/business_support_api.rb
317
316
  - lib/gds_api/test_helpers/business_support_helper.rb
318
- - lib/gds_api/test_helpers/collections_api.rb
319
317
  - lib/gds_api/test_helpers/common_responses.rb
320
318
  - lib/gds_api/test_helpers/content_api.rb
321
319
  - lib/gds_api/test_helpers/content_api/artefact_stub.rb
@@ -348,7 +346,6 @@ files:
348
346
  - lib/gds_api/worldwide.rb
349
347
  - test/asset_manager_test.rb
350
348
  - test/business_support_api_test.rb
351
- - test/collections_api_test.rb
352
349
  - test/content_api_test.rb
353
350
  - test/content_register_test.rb
354
351
  - test/content_store_test.rb
@@ -442,7 +439,6 @@ test_files:
442
439
  - test/response_test.rb
443
440
  - test/organisations_api_test.rb
444
441
  - test/imminence_api_test.rb
445
- - test/collections_api_test.rb
446
442
  - test/content_store_test.rb
447
443
  - test/asset_manager_test.rb
448
444
  - test/fixtures/hello.txt
@@ -1,15 +0,0 @@
1
- require_relative 'base'
2
- require_relative 'exceptions'
3
-
4
- class GdsApi::CollectionsApi < GdsApi::Base
5
-
6
- def topic(base_path, options={})
7
- get_json(collections_api_url(base_path, options))
8
- end
9
-
10
- private
11
-
12
- def collections_api_url(base_path, options={})
13
- "#{endpoint}/specialist-sectors#{base_path}#{query_string(options)}"
14
- end
15
- end
@@ -1,128 +0,0 @@
1
- require 'gds_api/test_helpers/json_client_helper'
2
- require 'json'
3
-
4
- module GdsApi
5
- module TestHelpers
6
- module CollectionsApi
7
- COLLECTIONS_API_ENDPOINT = Plek.current.find('collections-api')
8
-
9
- def collections_api_has_content_for(base_path, options={})
10
- body_options = options.delete(:return_body_options) || {}
11
-
12
- params = options.any? ? "?#{Rack::Utils.build_nested_query(options)}" : ''
13
- url = COLLECTIONS_API_ENDPOINT + "/specialist-sectors" + base_path + params
14
-
15
- stub_request(:get, url).to_return(
16
- status: 200,
17
- body: body_with_options(
18
- body_options.merge(base_path: base_path)
19
- ).to_json,
20
- )
21
- end
22
-
23
- def collections_api_has_no_content_for(base_path)
24
- url = COLLECTIONS_API_ENDPOINT + "/specialist-sectors" + base_path
25
-
26
- stub_request(:get, url).to_return(
27
- status: 404
28
- )
29
- end
30
-
31
- def collections_api_example_documents
32
- [
33
- {
34
- title: "Oil rig safety requirements",
35
- link: "http://example.com/documents/oil-rig-safety-requirements",
36
- public_updated_at: "2014-10-27T09:35:57+00:00",
37
- latest_change_note: "Updated topics"
38
- },
39
- {
40
- title: "Undersea piping restrictions",
41
- link: "http://example.com/documents/undersea-piping-restrictions",
42
- public_updated_at: "2014-10-15T09:36:18+01:00",
43
- latest_change_note: nil
44
- },
45
- {
46
- title: "North sea shipping lanes",
47
- link: "http://example.com/documents/north-sea-shipping-lanes",
48
- public_updated_at: nil,
49
- latest_change_note: "Corrected shipping lane"
50
- },
51
- {
52
- title: "Oil rig staffing",
53
- link: "http://example.com/documents/oil-rig-staffing",
54
- public_updated_at: "2014-09-22T09:37:00+01:00",
55
- latest_change_note: "Added annual leave allowances"
56
- },
57
- ]
58
- end
59
-
60
- private
61
-
62
- def body_with_options(options)
63
- {
64
- base_path: options.fetch(:base_path),
65
- title: 'Example title',
66
- description: 'example description',
67
- public_updated_at: "2014-03-04T13:58:11+00:00",
68
- parent: {
69
- id: "http://example.com/oil-and-gas",
70
- web_url: "http://example.com/browse/oil-and-gas",
71
- details: {
72
- description: nil,
73
- short_description: nil,
74
- type: "section",
75
- },
76
- content_with_tag: {
77
- id: "http://example.com/with_tag.json?section=oil-and-gas",
78
- web_url: "http://example.com/browse/oil-and-gas"
79
- },
80
- parent: nil,
81
- title: "Oil and gas",
82
- state: "live",
83
- },
84
- details: {
85
- groups: [
86
- # Curated content excluding untagged content
87
- {
88
- name: "Oil rigs",
89
- contents: [
90
- {
91
- web_url: "http://example.com/api/oil-rig-safety-requirements.json",
92
- title: "Oil rig safety requirements",
93
- },
94
- {
95
- web_url: "http://example.com/api/oil-rig-staffing.json",
96
- title: "Oil rig staffing",
97
- }
98
- ]
99
- },
100
- {
101
- name: "Piping",
102
- contents: [
103
- {
104
- web_url: "http://example.com/api/undersea-piping-restrictions.json",
105
- title: "Undersea piping restrictions",
106
- }
107
- ]
108
- },
109
- # Uncurated content
110
- {
111
- name: "Other",
112
- contents: [
113
- {
114
- web_url: "http://example.com/api/north-sea-shipping-lanes.json",
115
- title: "North sea shipping lanes",
116
- }
117
- ]
118
- }
119
- ],
120
- documents: collections_api_example_documents,
121
- documents_start: options.fetch(:start, 0),
122
- documents_total: options.fetch(:total, collections_api_example_documents.size),
123
- }
124
- }
125
- end
126
- end
127
- end
128
- end
@@ -1,30 +0,0 @@
1
- require 'test_helper'
2
- require 'gds_api/collections_api'
3
- require 'gds_api/test_helpers/collections_api'
4
-
5
- describe GdsApi::CollectionsApi do
6
- include GdsApi::TestHelpers::CollectionsApi
7
-
8
- before do
9
- @base_api_url = Plek.current.find("collections-api")
10
- @api = GdsApi::CollectionsApi.new(@base_api_url)
11
- end
12
-
13
- describe "topic" do
14
- it "should return the curated lists for a given base path" do
15
- base_path = "/test/base-path"
16
- collections_api_has_content_for(base_path)
17
- response = @api.topic(base_path)
18
- assert_equal base_path, response["base_path"]
19
- end
20
-
21
- it 'accepts "start" and "count" parameters for pagination' do
22
- base_path = "/test/base-path"
23
-
24
- collections_api_has_content_for(base_path, start: '10', count: '20')
25
- response = @api.topic(base_path, start: 10, count: 20)
26
-
27
- assert_equal base_path, response['base_path']
28
- end
29
- end
30
- end