shopify-api-limits 0.0.5 → 0.0.7
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.rdoc +21 -26
- data/lib/shopify-api-limits.rb +8 -14
- data/lib/shopify-api-limits/shopify_api/limits.rb +72 -0
- data/lib/shopify-api-limits/version.rb +1 -1
- data/spec/limits.rb +13 -11
- metadata +2 -2
- data/lib/shopify-api-limits/shopify_api/shopify_api.rb +0 -72
data/README.rdoc
CHANGED
@@ -23,28 +23,23 @@ ActiveResource does not make it easy to read the HTTP response headers, since th
|
|
23
23
|
end
|
24
24
|
|
25
25
|
== Solution
|
26
|
-
Hack ActiveResource::Connection to introduce a new attr_reader :response and
|
26
|
+
Hack ActiveResource::Connection to introduce a new attr_reader :response and capture the returned HTTPResponse instance from the #handle_response method.
|
27
27
|
|
28
|
-
|
28
|
+
module ActiveResource
|
29
29
|
class Connection
|
30
|
-
# HACK
|
30
|
+
# HACK: Add an attr_reader for response
|
31
31
|
attr_reader :response
|
32
32
|
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
@response = handle_response(result)
|
41
|
-
rescue Timeout::Error => e
|
42
|
-
raise TimeoutError.new(e.message)
|
43
|
-
rescue OpenSSL::SSL::SSLError => e
|
44
|
-
raise SSLError.new(e.message)
|
45
|
-
end
|
33
|
+
# capture the original #handle_response as an unbound method instead of using alias
|
34
|
+
handle_response = self.instance_method(:handle_response)
|
35
|
+
|
36
|
+
# re-implement #handle_response to capture the returned HTTPResponse to an instance var.
|
37
|
+
define_method(:handle_response) do |response|
|
38
|
+
@response = handle_response.bind(self).call(response)
|
39
|
+
end
|
46
40
|
end
|
47
|
-
end
|
41
|
+
end
|
42
|
+
|
48
43
|
|
49
44
|
Now it's possible to access the HTTPResponse instance directly from ActiveResource, via:
|
50
45
|
foo = ActiveResource::Base.connection.response['http-header-param-foo']
|
@@ -55,23 +50,23 @@ Now it's possible to access the HTTPResponse instance directly from ActiveResour
|
|
55
50
|
gem "shopify-api-limits"
|
56
51
|
|
57
52
|
== Usage
|
58
|
-
count_shop = ShopifyAPI.
|
59
|
-
limit_shop = ShopifyAPI.
|
53
|
+
count_shop = ShopifyAPI.credit_used :shop
|
54
|
+
limit_shop = ShopifyAPI.credit_limit :shop
|
60
55
|
|
61
|
-
count_global = ShopifyAPI.
|
62
|
-
limit_global = ShopifyAPI.
|
56
|
+
count_global = ShopifyAPI.credit_used :global
|
57
|
+
limit_global = ShopifyAPI.credit_limit :global
|
63
58
|
|
64
|
-
Generally, you shouldn't need to use the methods above directly -- rather they're used under-the-hood by the following helpful methods which don't require a scope (
|
59
|
+
Generally, you shouldn't need to use the methods above directly -- rather, they're used under-the-hood by the following helpful methods which don't require a scope (<b>:shop/:global</b>): If the <b>:global</b> scope has fewer calls available than the <b>:local</b> scope, the methods will operate upon the <b>:global</b> scope; otherwise, values will be returned based upon the <b>:shop</b> scope.
|
65
60
|
|
66
|
-
unless ShopifyAPI.
|
67
|
-
#make
|
61
|
+
unless ShopifyAPI.credit_maxed?
|
62
|
+
#make a ShopifyAPI call
|
68
63
|
end
|
69
64
|
|
70
|
-
until ShopifyAPI.
|
65
|
+
until ShopifyAPI.credit_maxed? || stop_condition
|
71
66
|
# make some ShopifyAPI calls
|
72
67
|
end
|
73
68
|
|
74
|
-
while ShopifyAPI.
|
69
|
+
while ShopifyAPI.credit_left || stop_condition
|
75
70
|
# make some ShopifyAPI calls
|
76
71
|
end
|
77
72
|
|
data/lib/shopify-api-limits.rb
CHANGED
@@ -4,22 +4,16 @@ module ShopifyAPI
|
|
4
4
|
module Limits
|
5
5
|
# Connection hack
|
6
6
|
require 'shopify-api-limits/active_resource/connection'
|
7
|
+
require 'shopify-api-limits/shopify_api/limits'
|
7
8
|
|
8
|
-
|
9
|
-
|
10
|
-
class Error < StandardError
|
11
|
-
def self.status_code(code = nil)
|
12
|
-
return @code unless code
|
13
|
-
@code = code
|
14
|
-
end
|
15
|
-
|
16
|
-
def status_code
|
17
|
-
self.class.status_code
|
18
|
-
end
|
9
|
+
def self.included(klass)
|
10
|
+
klass.send(:extend, ClassMethods)
|
19
11
|
end
|
20
|
-
|
21
|
-
class
|
22
|
-
class
|
12
|
+
|
13
|
+
class Error < StandardError; end
|
14
|
+
class GlobalError < Error; end
|
15
|
+
class ShopError < Error; end
|
16
|
+
|
23
17
|
end
|
24
18
|
end
|
25
19
|
|
@@ -0,0 +1,72 @@
|
|
1
|
+
module ShopifyAPI
|
2
|
+
module Limits
|
3
|
+
module ClassMethods
|
4
|
+
|
5
|
+
# Takes form num_requests_executed/max_requests
|
6
|
+
# Eg: 101/3000
|
7
|
+
CREDIT_LIMIT_HEADER_PARAM = {
|
8
|
+
:global => 'http_x_shopify_api_call_limit',
|
9
|
+
:shop => 'http_x_shopify_shop_api_call_limit'
|
10
|
+
}
|
11
|
+
|
12
|
+
##
|
13
|
+
# How many more API calls can I make?
|
14
|
+
# @return {Integer}
|
15
|
+
#
|
16
|
+
def credit_left
|
17
|
+
shop = credit_limit(:shop) - credit_used(:shop)
|
18
|
+
global = credit_limit(:global) - credit_used(:global)
|
19
|
+
shop < global ? shop : global
|
20
|
+
end
|
21
|
+
alias_method :available_calls, :credit_left
|
22
|
+
|
23
|
+
##
|
24
|
+
# Have I reached my API call limit?
|
25
|
+
# @return {Boolean}
|
26
|
+
#
|
27
|
+
def credit_maxed?
|
28
|
+
credit_left == 0
|
29
|
+
end
|
30
|
+
alias_method :maxed?, :credit_maxed?
|
31
|
+
|
32
|
+
##
|
33
|
+
# How many total API calls can I make?
|
34
|
+
# NOTE: subtracting 1 from credit_limit because I think ShopifyAPI cuts off at 299/2999 or shop/global limits.
|
35
|
+
# @param {Symbol} scope [:shop|:global]
|
36
|
+
# @return {Integer}
|
37
|
+
#
|
38
|
+
def credit_limit(scope=:shop)
|
39
|
+
@api_credit_limit ||= {}
|
40
|
+
@api_credit_limit[scope] ||= api_credit_limit_param(scope).pop.to_i - 1
|
41
|
+
end
|
42
|
+
alias_method :call_limit, :credit_limit
|
43
|
+
|
44
|
+
##
|
45
|
+
# How many API calls have I made?
|
46
|
+
# @param {Symbol} scope [:shop|:global]
|
47
|
+
# @return {Integer}
|
48
|
+
#
|
49
|
+
def credit_used(scope=:shop)
|
50
|
+
api_credit_limit_param(scope).shift.to_i
|
51
|
+
end
|
52
|
+
alias_method :call_count, :credit_used
|
53
|
+
|
54
|
+
##
|
55
|
+
# @return {HTTPResonse}
|
56
|
+
#
|
57
|
+
def response
|
58
|
+
Shop.current unless ActiveResource::Base.connection.response
|
59
|
+
ActiveResource::Base.connection.response
|
60
|
+
end
|
61
|
+
|
62
|
+
private
|
63
|
+
|
64
|
+
##
|
65
|
+
# @return {Array}
|
66
|
+
#
|
67
|
+
def api_credit_limit_param(scope)
|
68
|
+
response[CREDIT_LIMIT_HEADER_PARAM[scope]].split('/')
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
data/spec/limits.rb
CHANGED
@@ -3,30 +3,32 @@ require './spec/boot'
|
|
3
3
|
|
4
4
|
describe "Limits" do
|
5
5
|
it "Can fetch local limits" do
|
6
|
-
count = ShopifyAPI.
|
7
|
-
limit = ShopifyAPI.
|
6
|
+
count = ShopifyAPI.credit_used :shop
|
7
|
+
limit = ShopifyAPI.credit_limit :shop
|
8
8
|
|
9
|
-
(count < 300 && count > 0).should be_true
|
10
9
|
(count < limit).should be_true
|
11
|
-
|
12
|
-
|
10
|
+
(count > 0).should be_true
|
11
|
+
ShopifyAPI.credit_maxed?.should be_false
|
12
|
+
(ShopifyAPI.credit_left > 0).should be_true
|
13
13
|
end
|
14
14
|
|
15
15
|
it "Can fetch global limits" do
|
16
|
-
count = ShopifyAPI.
|
17
|
-
limit = ShopifyAPI.
|
16
|
+
count = ShopifyAPI.credit_used :global
|
17
|
+
limit = ShopifyAPI.creidt_limit :global
|
18
18
|
|
19
19
|
(count < 3000 && count > 0).should be_true
|
20
20
|
(count < limit).should be_true
|
21
|
-
ShopifyAPI.
|
22
|
-
(ShopifyAPI.
|
21
|
+
ShopifyAPI.credit_maxed?.should be_false
|
22
|
+
(ShopifyAPI.credit_left > 0).should be_true
|
23
23
|
end
|
24
24
|
|
25
25
|
it "Can execute up to local max" do
|
26
|
-
until ShopifyAPI.
|
26
|
+
until ShopifyAPI.credit_maxed?
|
27
27
|
ShopifyAPI::Shop.current
|
28
|
-
puts "avail: #{ShopifyAPI.
|
28
|
+
puts "avail: #{ShopifyAPI.credit_left}, maxed: #{ShopifyAPI.credit_maxed?}"
|
29
29
|
end
|
30
|
+
ShopifyAPI.credit_maxed?.should be_true
|
31
|
+
(ShopifyAPI.credit_left == 0).should be_true
|
30
32
|
end
|
31
33
|
|
32
34
|
end
|
metadata
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
name: shopify-api-limits
|
3
3
|
version: !ruby/object:Gem::Version
|
4
4
|
prerelease:
|
5
|
-
version: 0.0.
|
5
|
+
version: 0.0.7
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
8
8
|
- Chris Scott
|
@@ -62,7 +62,7 @@ files:
|
|
62
62
|
- Rakefile
|
63
63
|
- lib/shopify-api-limits.rb
|
64
64
|
- lib/shopify-api-limits/active_resource/connection.rb
|
65
|
-
- lib/shopify-api-limits/shopify_api/
|
65
|
+
- lib/shopify-api-limits/shopify_api/limits.rb
|
66
66
|
- lib/shopify-api-limits/version.rb
|
67
67
|
- shopify-api-limits.gemspec
|
68
68
|
- spec/boot.rb
|
@@ -1,72 +0,0 @@
|
|
1
|
-
module ShopifyAPI
|
2
|
-
module Limits
|
3
|
-
def self.included(klass)
|
4
|
-
klass.send(:extend, ClassMethods)
|
5
|
-
end
|
6
|
-
end
|
7
|
-
|
8
|
-
module ClassMethods
|
9
|
-
|
10
|
-
# Takes form num_requests_executed/max_requests
|
11
|
-
# Eg: 101/3000
|
12
|
-
CALL_LIMIT_HEADER_PARAM = {
|
13
|
-
:global => 'http_x_shopify_api_call_limit',
|
14
|
-
:shop => 'http_x_shopify_shop_api_call_limit'
|
15
|
-
}
|
16
|
-
|
17
|
-
##
|
18
|
-
# How many more API calls can I make?
|
19
|
-
# @return {Integer}
|
20
|
-
#
|
21
|
-
def available_calls
|
22
|
-
shop = call_limit(:shop) - call_count(:shop)
|
23
|
-
global = call_limit(:global) - call_count(:global)
|
24
|
-
shop < global ? shop : global
|
25
|
-
end
|
26
|
-
|
27
|
-
##
|
28
|
-
# Have I reached my API call limit?
|
29
|
-
# @return {Boolean}
|
30
|
-
#
|
31
|
-
def maxed?
|
32
|
-
available_calls == 0
|
33
|
-
end
|
34
|
-
|
35
|
-
##
|
36
|
-
# How many total API calls can I make?
|
37
|
-
# NOTE: subtracting 1 from call_limit because I think ShopifyAPI cuts off at 299/2999 or shop/global limits.
|
38
|
-
# @param {Symbol} scope [:shop|:global]
|
39
|
-
# @return {Integer}
|
40
|
-
#
|
41
|
-
def call_limit(scope=:shop)
|
42
|
-
@api_call_limit ||= {}
|
43
|
-
@api_call_limit[scope] ||= api_call_limit_param(scope).pop.to_i - 1
|
44
|
-
end
|
45
|
-
|
46
|
-
##
|
47
|
-
# How many API calls have I made?
|
48
|
-
# @param {Symbol} scope [:shop|:global]
|
49
|
-
# @return {Integer}
|
50
|
-
#
|
51
|
-
def call_count(scope=:shop)
|
52
|
-
api_call_limit_param(scope).shift.to_i
|
53
|
-
end
|
54
|
-
|
55
|
-
##
|
56
|
-
# @return {HTTPResonse}
|
57
|
-
#
|
58
|
-
def response
|
59
|
-
Shop.current unless ActiveResource::Base.connection.response
|
60
|
-
ActiveResource::Base.connection.response
|
61
|
-
end
|
62
|
-
|
63
|
-
private
|
64
|
-
|
65
|
-
##
|
66
|
-
# @return {Array}
|
67
|
-
#
|
68
|
-
def api_call_limit_param(scope)
|
69
|
-
response[CALL_LIMIT_HEADER_PARAM[scope]].split('/')
|
70
|
-
end
|
71
|
-
end
|
72
|
-
end
|