sucker 1.2.0 → 1.3.0.pre
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE +1 -1
- data/README.md +45 -20
- data/lib/sucker/parameters.rb +11 -7
- data/lib/sucker/parameters.rbc +723 -0
- data/lib/sucker/request.rb +52 -154
- data/lib/sucker/request.rbc +2719 -0
- data/lib/sucker/response.rb +14 -36
- data/lib/sucker/response.rbc +1307 -0
- data/lib/sucker/version.rb +3 -1
- data/lib/sucker/version.rbc +130 -0
- data/lib/sucker.rb +4 -2
- data/lib/sucker.rbc +286 -0
- data/spec/fixtures/cassette_library/0394751221.yml +26 -0
- data/spec/fixtures/cassette_library/0415246334.yml +26 -0
- data/spec/fixtures/cassette_library/0679753354.yml +26 -0
- data/spec/fixtures/cassette_library/0816614024-0007218095.yml +26 -0
- data/spec/fixtures/cassette_library/0816614024-0143105825.yml +26 -0
- data/spec/fixtures/cassette_library/0816614024.yml +26 -0
- data/spec/fixtures/cassette_library/482224816x.yml +26 -0
- data/spec/fixtures/cassette_library/816614024.yml +151 -0
- data/spec/fixtures/cassette_library/a2h6nh4sqyfz4m.yml +26 -0
- data/spec/fixtures/cassette_library/a2jyso6w6kep83.yml +26 -0
- data/spec/fixtures/cassette_library/author-lacan-or-deleuze-and-not-fiction.yml +26 -0
- data/spec/fixtures/cassette_library/b000aspues.yml +26 -0
- data/spec/fixtures/cassette_library/deleuze-binding-kindle.yml +26 -0
- data/spec/fixtures/cassette_library/deleuze.yml +26 -0
- data/spec/fixtures/cassette_library/george-orwell.yml +26 -0
- data/spec/fixtures/cassette_library/spec/sucker/request.yml +4 -4
- data/spec/fixtures/cassette_library/spec/sucker/response.yml +3 -3
- data/spec/spec_helper.rbc +230 -0
- data/spec/sucker/parameters_spec.rbc +1476 -0
- data/spec/sucker/request_spec.rb +34 -217
- data/spec/sucker/request_spec.rbc +2473 -0
- data/spec/sucker/response_spec.rb +46 -95
- data/spec/sucker/response_spec.rbc +2854 -0
- data/spec/sucker_spec.rbc +287 -0
- data/spec/support/amazon_credentials.rbc +154 -0
- data/spec/support/asins.rbc +335 -0
- data/spec/support/vcr.rbc +356 -0
- metadata +72 -96
- data/CHANGELOG.md +0 -47
data/lib/sucker/request.rb
CHANGED
@@ -1,6 +1,6 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require '
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require 'net/http'
|
4
4
|
require 'uri'
|
5
5
|
|
6
6
|
module Sucker #:nodoc:
|
@@ -14,16 +14,27 @@ module Sucker #:nodoc:
|
|
14
14
|
:ca => 'ecs.amazonaws.ca',
|
15
15
|
:fr => 'ecs.amazonaws.fr',
|
16
16
|
:jp => 'ecs.amazonaws.jp' }
|
17
|
-
PATH = "/onca/xml"
|
18
17
|
|
19
|
-
#
|
18
|
+
# Your Amazon associate tag
|
19
|
+
attr_accessor :associate_tag
|
20
|
+
|
21
|
+
# Your AWS access key
|
22
|
+
attr_accessor :key
|
23
|
+
|
24
|
+
# Local IP to route the request through
|
25
|
+
attr_accessor :local_ip
|
26
|
+
|
27
|
+
# Amazon locale
|
28
|
+
attr_accessor :locale
|
29
|
+
|
30
|
+
# Your AWS secret
|
20
31
|
attr_accessor :secret
|
21
32
|
|
22
33
|
# Initializes a request object
|
23
34
|
#
|
24
35
|
# worker = Sucker.new(
|
25
|
-
# :key =>
|
26
|
-
# :secret =>
|
36
|
+
# :key => 'API KEY',
|
37
|
+
# :secret => 'API SECRET')
|
27
38
|
#
|
28
39
|
def initialize(args)
|
29
40
|
args.each { |k, v| send("#{k}=", v) }
|
@@ -32,147 +43,23 @@ module Sucker #:nodoc:
|
|
32
43
|
# Merges a hash into the existing parameters
|
33
44
|
#
|
34
45
|
# worker << {
|
35
|
-
#
|
36
|
-
#
|
37
|
-
#
|
46
|
+
# 'Operation' => 'ItemLookup',
|
47
|
+
# 'IdType' => 'ASIN',
|
48
|
+
# 'ItemId' => '0816614024' }
|
38
49
|
#
|
39
50
|
def <<(hash)
|
40
51
|
self.parameters.merge!(hash)
|
41
52
|
end
|
42
53
|
|
43
|
-
# Returns the associate tag for the current locale
|
44
|
-
def associate_tag
|
45
|
-
@associate_tags[locale.to_sym] rescue ''
|
46
|
-
end
|
47
|
-
|
48
|
-
# Sets the associate tag for the current locale
|
49
|
-
#
|
50
|
-
# worker.associate_tag = 'foo-bar'
|
51
|
-
#
|
52
|
-
def associate_tag=(token)
|
53
|
-
associate_tags[locale.to_sym] = token
|
54
|
-
end
|
55
|
-
|
56
|
-
# Gets the associate tags for all locales
|
57
|
-
def associate_tags
|
58
|
-
@associate_tags ||= {}
|
59
|
-
end
|
60
|
-
|
61
|
-
# Sets associate tags for all locales
|
62
|
-
#
|
63
|
-
# You need a distinct associate tag for each locale.
|
64
|
-
#
|
65
|
-
# tags = {
|
66
|
-
# :us => 'foo-bar-10',
|
67
|
-
# :uk => 'foo-bar-20',
|
68
|
-
# ... }
|
69
|
-
#
|
70
|
-
# worker.associate_tags = tags
|
71
|
-
#
|
72
|
-
def associate_tags=(tokens)
|
73
|
-
@associate_tags = tokens
|
74
|
-
end
|
75
|
-
|
76
|
-
# Returns options for curl and yields them if given a block
|
77
|
-
#
|
78
|
-
# worker.curl_opts { |c| c.interface = "eth1" }
|
79
|
-
#
|
80
|
-
def curl_opts
|
81
|
-
@curl_opts ||= OpenStruct.new
|
82
|
-
yield @curl_opts if block_given?
|
83
|
-
|
84
|
-
@curl_opts.marshal_dump
|
85
|
-
end
|
86
|
-
|
87
54
|
# Performs a request and returns a response
|
88
55
|
#
|
89
56
|
# response = worker.get
|
90
57
|
#
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
# responses = worker.get(:us)
|
95
|
-
#
|
96
|
-
# responses = worker.get(:all)
|
97
|
-
#
|
98
|
-
def get(*args)
|
99
|
-
case args.count
|
100
|
-
|
101
|
-
when 0
|
102
|
-
curl = Curl::Easy.perform(uri.to_s) do |easy|
|
103
|
-
curl_opts.each { |k, v| easy.send("#{k}=", v) }
|
104
|
-
end
|
105
|
-
Response.new(curl)
|
106
|
-
|
107
|
-
when 1
|
108
|
-
arg = args.first
|
109
|
-
if arg == :all
|
110
|
-
get_multi locales
|
111
|
-
else
|
112
|
-
self.locale = arg
|
113
|
-
get
|
114
|
-
end
|
115
|
-
|
116
|
-
else
|
117
|
-
get_multi args
|
118
|
-
end
|
119
|
-
end
|
120
|
-
|
121
|
-
def get_all # :nodoc:
|
122
|
-
warn "[DEPRECATION] `get_all` is deprecated. Please use `get(:all) instead."
|
123
|
-
get(:all)
|
124
|
-
end
|
125
|
-
|
126
|
-
# Returns the AWS access key for the current locale
|
127
|
-
def key
|
128
|
-
raise ArgumentError.new "AWS access key missing" unless @keys[locale]
|
129
|
-
|
130
|
-
@keys[locale]
|
131
|
-
end
|
132
|
-
|
133
|
-
# Sets a global AWS access key
|
134
|
-
#
|
135
|
-
# worker.key = 'foo'
|
136
|
-
#
|
137
|
-
def key=(token)
|
138
|
-
@keys = locales.inject({}) do |keys, locale|
|
139
|
-
keys[locale] = token
|
140
|
-
keys
|
58
|
+
def get
|
59
|
+
response = request_through(local_ip) do
|
60
|
+
Net::HTTP.get_response(uri)
|
141
61
|
end
|
142
|
-
|
143
|
-
|
144
|
-
# Sets distinct AWS access keys for the locales
|
145
|
-
#
|
146
|
-
# You can use the same key on multiple venues. Caveat: Calls against (1) the US
|
147
|
-
# and Canada and (2) the UK, France, and Germany count against the same call
|
148
|
-
# rate quota.
|
149
|
-
#
|
150
|
-
# keys = {
|
151
|
-
# :us => 'foo',
|
152
|
-
# :uk => 'bar',
|
153
|
-
# ... }
|
154
|
-
#
|
155
|
-
# worker.keys = keys
|
156
|
-
#
|
157
|
-
def keys=(tokens)
|
158
|
-
@keys = tokens
|
159
|
-
end
|
160
|
-
|
161
|
-
def locale
|
162
|
-
raise ArgumentError.new "Locale not set" unless @locale
|
163
|
-
|
164
|
-
@locale
|
165
|
-
end
|
166
|
-
|
167
|
-
# Sets the current Amazon locale
|
168
|
-
#
|
169
|
-
# Valid values are :us, :uk, :de, :ca, :fr, and :jp.
|
170
|
-
def locale=(new_locale)
|
171
|
-
new_locale = new_locale.to_sym
|
172
|
-
|
173
|
-
raise ArgumentError.new "Invalid locale" unless locales.include? new_locale
|
174
|
-
|
175
|
-
@locale = new_locale
|
62
|
+
Response.new(response)
|
176
63
|
end
|
177
64
|
|
178
65
|
# The parameters to query Amazon with
|
@@ -194,7 +81,7 @@ module Sucker #:nodoc:
|
|
194
81
|
parameters.
|
195
82
|
normalize.
|
196
83
|
merge({ 'AWSAccessKeyId' => key }).
|
197
|
-
merge({ 'AssociateTag' => associate_tag }).
|
84
|
+
merge({ 'AssociateTag' => associate_tag.to_s }).
|
198
85
|
sort.
|
199
86
|
map do |k, v|
|
200
87
|
"#{k}=" + escape(v)
|
@@ -205,7 +92,7 @@ module Sucker #:nodoc:
|
|
205
92
|
query = build_query
|
206
93
|
|
207
94
|
digest = OpenSSL::Digest::Digest.new('sha256')
|
208
|
-
string = ['GET', host,
|
95
|
+
string = ['GET', host, '/onca/xml', query].join("\n")
|
209
96
|
hmac = OpenSSL::HMAC.digest(digest, secret, string)
|
210
97
|
signature = escape([hmac].pack('m').chomp)
|
211
98
|
|
@@ -218,30 +105,41 @@ module Sucker #:nodoc:
|
|
218
105
|
end
|
219
106
|
end
|
220
107
|
|
221
|
-
def
|
222
|
-
|
108
|
+
def host
|
109
|
+
HOSTS[locale]
|
110
|
+
end
|
111
|
+
|
112
|
+
def request_through(local_ip)
|
113
|
+
if local_ip
|
114
|
+
TCPSocket.instance_eval do
|
115
|
+
(class << self; self; end).instance_eval do
|
116
|
+
alias_method :orig_open, :open
|
223
117
|
|
224
|
-
|
225
|
-
|
226
|
-
|
227
|
-
|
118
|
+
define_method(:open) do |conn_address, conn_port|
|
119
|
+
original_open(conn_address, conn_port, local_ip)
|
120
|
+
end
|
121
|
+
end
|
122
|
+
end
|
228
123
|
end
|
229
124
|
|
230
|
-
|
231
|
-
end
|
125
|
+
return_value = yield
|
232
126
|
|
233
|
-
|
234
|
-
|
235
|
-
|
127
|
+
if local_ip
|
128
|
+
TCPSocket.instance_eval do
|
129
|
+
(class << self; self; end).instance_eval do
|
130
|
+
alias_method :open, :orig_open
|
131
|
+
remove_method :orig_open
|
132
|
+
end
|
133
|
+
end
|
134
|
+
end
|
236
135
|
|
237
|
-
|
238
|
-
@locales ||= HOSTS.keys
|
136
|
+
return_value
|
239
137
|
end
|
240
138
|
|
241
139
|
def uri
|
242
140
|
URI::HTTP.build(
|
243
141
|
:host => host,
|
244
|
-
:path =>
|
142
|
+
:path => '/onca/xml',
|
245
143
|
:query => build_signed_query)
|
246
144
|
end
|
247
145
|
|