vacuum 0.1.3 → 0.2.0.pre
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.
- data/README.md +69 -27
- data/lib/vacuum/endpoint/base.rb +58 -0
- data/lib/vacuum/endpoint/mws.rb +59 -0
- data/lib/vacuum/endpoint/product_advertising.rb +34 -0
- data/lib/vacuum/mws.rb +8 -0
- data/lib/vacuum/product_advertising.rb +7 -0
- data/lib/vacuum/request/base.rb +96 -0
- data/lib/vacuum/request/mws.rb +24 -0
- data/lib/vacuum/request/product_advertising.rb +90 -0
- data/lib/vacuum/request/signature/authentication.rb +32 -0
- data/lib/vacuum/request/signature/builder.rb +70 -0
- data/lib/vacuum/request/utils.rb +24 -0
- data/lib/vacuum/response/base.rb +57 -0
- data/lib/vacuum/response/mws.rb +7 -0
- data/lib/vacuum/response/product_advertising.rb +19 -0
- data/lib/vacuum/response/utils.rb +48 -0
- data/lib/vacuum/version.rb +1 -1
- data/lib/vacuum.rb +31 -11
- data/spec/fixtures/{http_response → product_advertising} +0 -0
- data/spec/spec_helper.rb +5 -4
- data/spec/support/shared_examples/endpoint.rb +43 -0
- data/spec/support/shared_examples/request.rb +95 -0
- data/spec/support/shared_examples/response.rb +51 -0
- data/spec/vacuum/endpoint/base_spec.rb +19 -0
- data/spec/vacuum/endpoint/mws_spec.rb +47 -0
- data/spec/vacuum/endpoint/product_advertising_spec.rb +25 -0
- data/spec/vacuum/request/base_spec.rb +22 -0
- data/spec/vacuum/request/mws_spec.rb +26 -0
- data/spec/vacuum/request/product_advertising_spec.rb +104 -0
- data/spec/vacuum/request/signature/authentication_spec.rb +30 -0
- data/spec/vacuum/request/signature/builder_spec.rb +76 -0
- data/spec/vacuum/request/utils_spec.rb +23 -0
- data/spec/vacuum/response/base_spec.rb +38 -0
- data/spec/vacuum/response/product_advertising_spec.rb +57 -0
- data/spec/vacuum/response/utils_spec.rb +42 -0
- metadata +107 -21
- data/lib/vacuum/em.rb +0 -21
- data/lib/vacuum/request.rb +0 -119
- data/lib/vacuum/response.rb +0 -63
- data/spec/vacuum/request_spec.rb +0 -130
- data/spec/vacuum/response_spec.rb +0 -80
@@ -0,0 +1,76 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
module Vacuum
|
4
|
+
module Request
|
5
|
+
module Signature
|
6
|
+
describe Builder do
|
7
|
+
let :url do
|
8
|
+
Addressable::URI.parse 'http://example.com/foo?bar=1'
|
9
|
+
end
|
10
|
+
|
11
|
+
let :builder do
|
12
|
+
described_class.new env, 'secret'
|
13
|
+
end
|
14
|
+
|
15
|
+
let :env do
|
16
|
+
{ :method => :get, :url => url }
|
17
|
+
end
|
18
|
+
|
19
|
+
describe '#method' do
|
20
|
+
it 'returns an HTTP method' do
|
21
|
+
builder.method.should eql 'GET'
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
describe '#sign' do
|
26
|
+
it 'signs the request' do
|
27
|
+
builder.sign
|
28
|
+
builder.url.query.should include 'Signature='
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
describe '#signature' do
|
33
|
+
after do
|
34
|
+
builder.signature
|
35
|
+
end
|
36
|
+
|
37
|
+
it 'generates an HMAC-SHA signature' do
|
38
|
+
OpenSSL::HMAC.should_receive(:digest).and_return 'secret'
|
39
|
+
end
|
40
|
+
|
41
|
+
it 'base64-encodes generated signature' do
|
42
|
+
Base64.should_receive(:encode64).and_return 'a string'
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
describe '#sort_query' do
|
47
|
+
it 'sorts query values' do
|
48
|
+
url.query = 'baz=0&bar=1'
|
49
|
+
builder.sort_query
|
50
|
+
builder.url.query.should eql 'bar=1&baz=0'
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
describe '#string_to_sign' do
|
55
|
+
it 'concatenates the request method, host, path, and query' do
|
56
|
+
expected_string = %w(GET example.com /foo bar=1).join "\n"
|
57
|
+
builder.string_to_sign.should eql expected_string
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
describe '#timestamp' do
|
62
|
+
it 'timestamps the request' do
|
63
|
+
builder.timestamp
|
64
|
+
builder.url.query.should include 'Timestamp='
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
describe '#url' do
|
69
|
+
it 'returns the request URL' do
|
70
|
+
builder.url.should be_an Addressable::URI
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
module Vacuum
|
4
|
+
module Request
|
5
|
+
describe Utils do
|
6
|
+
describe '.camelize' do
|
7
|
+
it 'camelizes an underscored String' do
|
8
|
+
Utils.camelize('foo_bar').should eql 'FooBar'
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
describe '.encode' do
|
13
|
+
it 'encodes reserved characters' do
|
14
|
+
Utils.encode(',').should eql '%2C'
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'does not encode unreserved characters' do
|
18
|
+
Utils.encode('~').should eql '~'
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
module Vacuum
|
4
|
+
module Response
|
5
|
+
describe Base do
|
6
|
+
let(:body) do
|
7
|
+
'<?xml version="1.0" ?>
|
8
|
+
<children>
|
9
|
+
<child>
|
10
|
+
<name>foo</name>
|
11
|
+
</child>
|
12
|
+
<child>
|
13
|
+
<name>bar</name>
|
14
|
+
</child>
|
15
|
+
</children>'.gsub />\s+</, '><'
|
16
|
+
end
|
17
|
+
|
18
|
+
let(:response) do
|
19
|
+
described_class.new body, '200'
|
20
|
+
end
|
21
|
+
|
22
|
+
it_behaves_like 'a response'
|
23
|
+
|
24
|
+
describe '#find' do
|
25
|
+
it 'returns an array of matches' do
|
26
|
+
response.find('child').should_not be_empty
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'yields matches to a block' do
|
30
|
+
names = response.find('child') do |child|
|
31
|
+
child['name']
|
32
|
+
end
|
33
|
+
names.should =~ %w(foo bar)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
@@ -0,0 +1,57 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
module Vacuum
|
4
|
+
module Response
|
5
|
+
describe ProductAdvertising do
|
6
|
+
let(:response) do
|
7
|
+
path = File.expand_path('../../../fixtures/product_advertising', __FILE__)
|
8
|
+
body = File.read path
|
9
|
+
|
10
|
+
described_class.new body, '200'
|
11
|
+
end
|
12
|
+
|
13
|
+
it_behaves_like 'a response'
|
14
|
+
|
15
|
+
context 'when Amazon returns errors' do
|
16
|
+
before do
|
17
|
+
response.body = <<-EOF.gsub!(/>\s+</, '><').strip!
|
18
|
+
<?xml version=\"1.0\" ?>
|
19
|
+
<Response xmlns="http://example.com">
|
20
|
+
<Errors>
|
21
|
+
<Error>foo</Error>
|
22
|
+
</Errors>
|
23
|
+
</Response>
|
24
|
+
EOF
|
25
|
+
end
|
26
|
+
|
27
|
+
describe '#errors' do
|
28
|
+
it 'returns an Array of errors' do
|
29
|
+
response.errors.should =~ ['foo']
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
describe '#has_errors?' do
|
35
|
+
context 'when response does not contain any errors' do
|
36
|
+
before do
|
37
|
+
response.stub!(:errors).and_return([])
|
38
|
+
end
|
39
|
+
|
40
|
+
it 'returns false' do
|
41
|
+
response.should_not have_errors
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
context 'when response contains errors' do
|
46
|
+
before do
|
47
|
+
response.stub!(:errors).and_return([1])
|
48
|
+
end
|
49
|
+
|
50
|
+
it 'returns true' do
|
51
|
+
response.should have_errors
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
module Vacuum
|
4
|
+
module Response
|
5
|
+
describe Utils do
|
6
|
+
describe '.xml_to_hash' do
|
7
|
+
let(:hash) do
|
8
|
+
str = <<-XML.gsub!(/>\s+</, '><').strip!
|
9
|
+
<?xml version=\"1.0\" ?>
|
10
|
+
<ItemAttributes>
|
11
|
+
<Title>Anti-Oedipus</Title>
|
12
|
+
<Author>Gilles Deleuze</Author>
|
13
|
+
<Author>Felix Guattari</Author>
|
14
|
+
<Creator Role="Translator">Robert Hurley</Creator>
|
15
|
+
</ItemAttributes>
|
16
|
+
XML
|
17
|
+
xml = Nokogiri::XML.parse str
|
18
|
+
|
19
|
+
Utils.xml_to_hash xml
|
20
|
+
end
|
21
|
+
|
22
|
+
it 'returns a hash' do
|
23
|
+
hash.should be_an_instance_of Hash
|
24
|
+
end
|
25
|
+
|
26
|
+
it 'handles only childs' do
|
27
|
+
hash['Title'].should eql 'Anti-Oedipus'
|
28
|
+
end
|
29
|
+
|
30
|
+
it 'handles arrays' do
|
31
|
+
hash['Author'].should be_a Array
|
32
|
+
end
|
33
|
+
|
34
|
+
it 'handles attributes' do
|
35
|
+
node = hash['Creator']
|
36
|
+
node['Role'].should eql 'Translator'
|
37
|
+
node['__content__'].should eql 'Robert Hurley'
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
metadata
CHANGED
@@ -1,46 +1,119 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: vacuum
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
5
|
-
prerelease:
|
4
|
+
version: 0.2.0.pre
|
5
|
+
prerelease: 6
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
8
8
|
- Hakan Ensari
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-
|
12
|
+
date: 2012-04-02 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
|
-
name:
|
16
|
-
requirement: &
|
15
|
+
name: rake
|
16
|
+
requirement: &70296598618460 !ruby/object:Gem::Requirement
|
17
17
|
none: false
|
18
18
|
requirements:
|
19
19
|
- - ~>
|
20
20
|
- !ruby/object:Gem::Version
|
21
|
-
version: '
|
21
|
+
version: '0.9'
|
22
|
+
type: :development
|
23
|
+
prerelease: false
|
24
|
+
version_requirements: *70296598618460
|
25
|
+
- !ruby/object:Gem::Dependency
|
26
|
+
name: rspec
|
27
|
+
requirement: &70296598617960 !ruby/object:Gem::Requirement
|
28
|
+
none: false
|
29
|
+
requirements:
|
30
|
+
- - ~>
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: '2.9'
|
33
|
+
type: :development
|
34
|
+
prerelease: false
|
35
|
+
version_requirements: *70296598617960
|
36
|
+
- !ruby/object:Gem::Dependency
|
37
|
+
name: addressable
|
38
|
+
requirement: &70296598617500 !ruby/object:Gem::Requirement
|
39
|
+
none: false
|
40
|
+
requirements:
|
41
|
+
- - ~>
|
42
|
+
- !ruby/object:Gem::Version
|
43
|
+
version: '2.2'
|
44
|
+
type: :runtime
|
45
|
+
prerelease: false
|
46
|
+
version_requirements: *70296598617500
|
47
|
+
- !ruby/object:Gem::Dependency
|
48
|
+
name: faraday
|
49
|
+
requirement: &70296598617040 !ruby/object:Gem::Requirement
|
50
|
+
none: false
|
51
|
+
requirements:
|
52
|
+
- - ~>
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: 0.7.6
|
55
|
+
type: :runtime
|
56
|
+
prerelease: false
|
57
|
+
version_requirements: *70296598617040
|
58
|
+
- !ruby/object:Gem::Dependency
|
59
|
+
name: nokogiri
|
60
|
+
requirement: &70296598616580 !ruby/object:Gem::Requirement
|
61
|
+
none: false
|
62
|
+
requirements:
|
63
|
+
- - ~>
|
64
|
+
- !ruby/object:Gem::Version
|
65
|
+
version: '1.5'
|
22
66
|
type: :runtime
|
23
67
|
prerelease: false
|
24
|
-
version_requirements: *
|
25
|
-
description: Vacuum is a
|
68
|
+
version_requirements: *70296598616580
|
69
|
+
description: ! 'Vacuum is a wrapper to various Amazon Web Services (AWS) APIs, including
|
70
|
+
|
71
|
+
Product Advertising and Marketplace Web Services (MWS).
|
72
|
+
|
73
|
+
'
|
26
74
|
email:
|
27
75
|
- hakan.ensari@papercavalier.com
|
28
76
|
executables: []
|
29
77
|
extensions: []
|
30
78
|
extra_rdoc_files: []
|
31
79
|
files:
|
32
|
-
- lib/vacuum/
|
33
|
-
- lib/vacuum/
|
34
|
-
- lib/vacuum/
|
80
|
+
- lib/vacuum/endpoint/base.rb
|
81
|
+
- lib/vacuum/endpoint/mws.rb
|
82
|
+
- lib/vacuum/endpoint/product_advertising.rb
|
83
|
+
- lib/vacuum/mws.rb
|
84
|
+
- lib/vacuum/product_advertising.rb
|
85
|
+
- lib/vacuum/request/base.rb
|
86
|
+
- lib/vacuum/request/mws.rb
|
87
|
+
- lib/vacuum/request/product_advertising.rb
|
88
|
+
- lib/vacuum/request/signature/authentication.rb
|
89
|
+
- lib/vacuum/request/signature/builder.rb
|
90
|
+
- lib/vacuum/request/utils.rb
|
91
|
+
- lib/vacuum/response/base.rb
|
92
|
+
- lib/vacuum/response/mws.rb
|
93
|
+
- lib/vacuum/response/product_advertising.rb
|
94
|
+
- lib/vacuum/response/utils.rb
|
35
95
|
- lib/vacuum/version.rb
|
36
96
|
- lib/vacuum.rb
|
37
97
|
- LICENSE
|
38
98
|
- README.md
|
39
|
-
- spec/fixtures/
|
99
|
+
- spec/fixtures/product_advertising
|
40
100
|
- spec/spec_helper.rb
|
41
|
-
- spec/
|
42
|
-
- spec/
|
43
|
-
|
101
|
+
- spec/support/shared_examples/endpoint.rb
|
102
|
+
- spec/support/shared_examples/request.rb
|
103
|
+
- spec/support/shared_examples/response.rb
|
104
|
+
- spec/vacuum/endpoint/base_spec.rb
|
105
|
+
- spec/vacuum/endpoint/mws_spec.rb
|
106
|
+
- spec/vacuum/endpoint/product_advertising_spec.rb
|
107
|
+
- spec/vacuum/request/base_spec.rb
|
108
|
+
- spec/vacuum/request/mws_spec.rb
|
109
|
+
- spec/vacuum/request/product_advertising_spec.rb
|
110
|
+
- spec/vacuum/request/signature/authentication_spec.rb
|
111
|
+
- spec/vacuum/request/signature/builder_spec.rb
|
112
|
+
- spec/vacuum/request/utils_spec.rb
|
113
|
+
- spec/vacuum/response/base_spec.rb
|
114
|
+
- spec/vacuum/response/product_advertising_spec.rb
|
115
|
+
- spec/vacuum/response/utils_spec.rb
|
116
|
+
homepage: https://github.com/hakanensari/vacuum
|
44
117
|
licenses: []
|
45
118
|
post_install_message:
|
46
119
|
rdoc_options: []
|
@@ -55,17 +128,30 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
55
128
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
56
129
|
none: false
|
57
130
|
requirements:
|
58
|
-
- - ! '
|
131
|
+
- - ! '>'
|
59
132
|
- !ruby/object:Gem::Version
|
60
|
-
version:
|
133
|
+
version: 1.3.1
|
61
134
|
requirements: []
|
62
135
|
rubyforge_project:
|
63
136
|
rubygems_version: 1.8.11
|
64
137
|
signing_key:
|
65
138
|
specification_version: 3
|
66
|
-
summary: A
|
139
|
+
summary: A wrapper to various Amazon Web Services APIs
|
67
140
|
test_files:
|
68
|
-
- spec/fixtures/
|
141
|
+
- spec/fixtures/product_advertising
|
69
142
|
- spec/spec_helper.rb
|
70
|
-
- spec/
|
71
|
-
- spec/
|
143
|
+
- spec/support/shared_examples/endpoint.rb
|
144
|
+
- spec/support/shared_examples/request.rb
|
145
|
+
- spec/support/shared_examples/response.rb
|
146
|
+
- spec/vacuum/endpoint/base_spec.rb
|
147
|
+
- spec/vacuum/endpoint/mws_spec.rb
|
148
|
+
- spec/vacuum/endpoint/product_advertising_spec.rb
|
149
|
+
- spec/vacuum/request/base_spec.rb
|
150
|
+
- spec/vacuum/request/mws_spec.rb
|
151
|
+
- spec/vacuum/request/product_advertising_spec.rb
|
152
|
+
- spec/vacuum/request/signature/authentication_spec.rb
|
153
|
+
- spec/vacuum/request/signature/builder_spec.rb
|
154
|
+
- spec/vacuum/request/utils_spec.rb
|
155
|
+
- spec/vacuum/response/base_spec.rb
|
156
|
+
- spec/vacuum/response/product_advertising_spec.rb
|
157
|
+
- spec/vacuum/response/utils_spec.rb
|
data/lib/vacuum/em.rb
DELETED
@@ -1,21 +0,0 @@
|
|
1
|
-
require 'vacuum'
|
2
|
-
require 'em-http-request'
|
3
|
-
|
4
|
-
module Vacuum
|
5
|
-
class Request
|
6
|
-
# Performs an async request.
|
7
|
-
#
|
8
|
-
# @param err [Proc] A callback to be executed if request fails
|
9
|
-
# @yield Passes response to given block
|
10
|
-
def aget(err = nil, &blk)
|
11
|
-
http = EM::HttpRequest.new(url).get
|
12
|
-
# @todo Consider using a SAX parser that can work on the chunks as they
|
13
|
-
# come in?
|
14
|
-
# http.stream { |chunk| parse chunk }
|
15
|
-
http.callback do
|
16
|
-
yield Response.new http.response, http.response_header.status
|
17
|
-
end
|
18
|
-
http.errback &err if err
|
19
|
-
end
|
20
|
-
end
|
21
|
-
end
|
data/lib/vacuum/request.rb
DELETED
@@ -1,119 +0,0 @@
|
|
1
|
-
module Vacuum
|
2
|
-
# A wrapper around the request to the Amazon Product Advertising API.
|
3
|
-
class Request
|
4
|
-
# The latest Amazon API version.
|
5
|
-
CURRENT_API_VERSION = '2011-08-01'
|
6
|
-
|
7
|
-
# A list of Amazon endpoints.
|
8
|
-
HOSTS = {
|
9
|
-
:ca => 'ecs.amazonaws.ca',
|
10
|
-
:cn => 'webservices.amazon.cn',
|
11
|
-
:de => 'ecs.amazonaws.de',
|
12
|
-
:es => 'webservices.amazon.es',
|
13
|
-
:fr => 'ecs.amazonaws.fr',
|
14
|
-
:it => 'webservices.amazon.it',
|
15
|
-
:jp => 'ecs.amazonaws.jp',
|
16
|
-
:uk => 'ecs.amazonaws.co.uk',
|
17
|
-
:us => 'ecs.amazonaws.com'
|
18
|
-
}
|
19
|
-
|
20
|
-
# Creates a new request for given locale and credentials.
|
21
|
-
#
|
22
|
-
# @param [Hash] options
|
23
|
-
# @option opts [#to_sym] :locale An Amazon locale
|
24
|
-
# @option opts [String] :key An Amazon AWS access key ID
|
25
|
-
# @option opts [String] :secret An Amazon AWS access secret key
|
26
|
-
# @option opts [String] :tag An Amazon Associate tag
|
27
|
-
# @raise [MissingKey] An Amazon AWS access key ID was not given
|
28
|
-
# @raise [MissingSecret] An Amazon AWS secret key was not given
|
29
|
-
# @raise [MissingTag] An Amazon Associate tag was not given
|
30
|
-
# @return [self]
|
31
|
-
def initialize(options)
|
32
|
-
_reset!
|
33
|
-
|
34
|
-
locale = (options[:locale] || :us).to_sym
|
35
|
-
@host = HOSTS[locale] or raise BadLocale
|
36
|
-
@key = options[:key] or raise MissingKey
|
37
|
-
@secret = options[:secret] or raise MissingSecret
|
38
|
-
@tag = options[:tag] or raise MissingTag
|
39
|
-
end
|
40
|
-
|
41
|
-
# Merges given parameters into the request query.
|
42
|
-
#
|
43
|
-
# @param [Hash] hsh Pairs of keys and values
|
44
|
-
# @return [self]
|
45
|
-
def build(hsh)
|
46
|
-
hsh.each do |k, v|
|
47
|
-
@params[k] = v.is_a?(Array) ? v.join(',') : v.to_s
|
48
|
-
end
|
49
|
-
|
50
|
-
self
|
51
|
-
end
|
52
|
-
|
53
|
-
# Replaces the request query with given parameters.
|
54
|
-
#
|
55
|
-
# @see(#build)
|
56
|
-
def build!(hsh = {})
|
57
|
-
_reset!
|
58
|
-
build hsh
|
59
|
-
end
|
60
|
-
|
61
|
-
# Performs a request.
|
62
|
-
#
|
63
|
-
# @return [Vacuum::Response] A response
|
64
|
-
def get
|
65
|
-
res = Net::HTTP.get_response(url)
|
66
|
-
Response.new(res.body, res.code)
|
67
|
-
end
|
68
|
-
|
69
|
-
# @return [Hash] The parameters that make up the request query.
|
70
|
-
def params
|
71
|
-
_default_params.merge(@params)
|
72
|
-
end
|
73
|
-
|
74
|
-
# @return [URI::HTTP] The URL for the API request
|
75
|
-
def url
|
76
|
-
URI::HTTP.build :host => @host,
|
77
|
-
:path => '/onca/xml',
|
78
|
-
:query => _query_string
|
79
|
-
end
|
80
|
-
|
81
|
-
private
|
82
|
-
|
83
|
-
def _default_params
|
84
|
-
default = {
|
85
|
-
'AWSAccessKeyId' => @key,
|
86
|
-
'AssociateTag' => @tag,
|
87
|
-
'Service' => 'AWSECommerceService',
|
88
|
-
'Timestamp' => _timestamp,
|
89
|
-
'Version' => CURRENT_API_VERSION
|
90
|
-
}
|
91
|
-
end
|
92
|
-
|
93
|
-
def _escape(value)
|
94
|
-
value.gsub(/([^a-zA-Z0-9_.~-]+)/) do
|
95
|
-
'%' + $1.unpack('H2' * $1.bytesize).join('%').upcase
|
96
|
-
end
|
97
|
-
end
|
98
|
-
|
99
|
-
def _query_string
|
100
|
-
qs = params.sort.map { |k, v| "#{k}=" + _escape(v) }.join('&')
|
101
|
-
|
102
|
-
# Sign query string.
|
103
|
-
dig = OpenSSL::Digest::Digest.new 'sha256'
|
104
|
-
req = ['GET', @host, '/onca/xml', qs]
|
105
|
-
hmac = OpenSSL::HMAC.digest dig, @secret, req.join("\n")
|
106
|
-
sig = _escape [hmac].pack('m').chomp
|
107
|
-
|
108
|
-
"#{qs}&Signature=#{sig}"
|
109
|
-
end
|
110
|
-
|
111
|
-
def _reset!
|
112
|
-
@params = {}
|
113
|
-
end
|
114
|
-
|
115
|
-
def _timestamp
|
116
|
-
Time.now.utc.iso8601
|
117
|
-
end
|
118
|
-
end
|
119
|
-
end
|
data/lib/vacuum/response.rb
DELETED
@@ -1,63 +0,0 @@
|
|
1
|
-
module Vacuum
|
2
|
-
# A wrapper around the API response.
|
3
|
-
class Response
|
4
|
-
|
5
|
-
# @return [String] body The response body
|
6
|
-
attr_accessor :body
|
7
|
-
|
8
|
-
# @return [Integer] code The HTTP status code of the response
|
9
|
-
attr_accessor :code
|
10
|
-
|
11
|
-
# Creates a new response.
|
12
|
-
#
|
13
|
-
# @param [String] body The response body
|
14
|
-
# @param [#to_i] code The HTTP status code of the response
|
15
|
-
def initialize(body, code)
|
16
|
-
@body = body
|
17
|
-
@code = code.to_i
|
18
|
-
end
|
19
|
-
|
20
|
-
# @return [Array] Errors in the response
|
21
|
-
def errors
|
22
|
-
find 'Error'
|
23
|
-
end
|
24
|
-
|
25
|
-
# Queries for a given attribute, yielding matching nodes to a block if
|
26
|
-
# given one.
|
27
|
-
#
|
28
|
-
# @param [String] Query attribute to be queried
|
29
|
-
# @yield Optionally passes matching nodes to a given block
|
30
|
-
# @return [Array] Matches
|
31
|
-
#
|
32
|
-
# @example
|
33
|
-
# items = res.find('Item')
|
34
|
-
# asins = res.find('Item') { |item| item['ASIN'] }
|
35
|
-
#
|
36
|
-
def find(query)
|
37
|
-
xml.xpath("//xmlns:#{query}").map do |node|
|
38
|
-
hsh = Knack.from_xml node
|
39
|
-
block_given? ? yield(hsh) : hsh
|
40
|
-
end
|
41
|
-
end
|
42
|
-
|
43
|
-
# @return [true, false] Whether the response has errors
|
44
|
-
def has_errors?
|
45
|
-
errors.count > 0
|
46
|
-
end
|
47
|
-
|
48
|
-
# @return [Hash] A hash representation of the entire response.
|
49
|
-
def to_hash
|
50
|
-
Knack.from_xml xml
|
51
|
-
end
|
52
|
-
|
53
|
-
# @return [true, false] Whether the HTTP response is OK
|
54
|
-
def valid?
|
55
|
-
code == 200
|
56
|
-
end
|
57
|
-
|
58
|
-
# @return [Nokogiri::XML] the XML document
|
59
|
-
def xml
|
60
|
-
@xml ||= Nokogiri::XML @body
|
61
|
-
end
|
62
|
-
end
|
63
|
-
end
|