apisonator 3.0.0 → 3.2.1

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
  SHA256:
3
- metadata.gz: 455379ea79ee4377baa1060f0213d37d08c66135c6a0be9233536de917968303
4
- data.tar.gz: d46f21858ba98539d51b0a32582e9b82c2ff6d08cbacb1b791d6cb9ea782024e
3
+ metadata.gz: 1f414f062cdabb59cdcc29b67a862a4400baa6e8d92ebeec909907ed881aa806
4
+ data.tar.gz: 2db24643307830c7cb2cef21da16a51aae8f9336b7bf35f90d4f22f82d15ff45
5
5
  SHA512:
6
- metadata.gz: 5df4b993ffd0dd16cc9d75b4dc88652cba83d0767c967d10777191010ea87a8db4cf0b824adc3879e47e4221ff5a48cfdfe54954b76b4fb4537b8a514fe91caf
7
- data.tar.gz: ee54b488232e0cf277d7bf052bbaab9edb96ba582b18859a7053a57a07ee50b9e932ed471e26a84cd60b9c7052c444b9595d07f98eb7d937eb83e4a5b28a1118
6
+ metadata.gz: 71ad48dc02408cab0de7f8264832489a08b935f55b47139a81ee7228cd71c783d8ebe81c7737c9b3035327535bd9b561784838486194e4b2ab808bb740fad753
7
+ data.tar.gz: 843744f70251b4d26365ab1fe2a4e7c73444b57629f3815c6043bbe467c70835050fdaabdd458e47323a11fb4294b01d1674dd5215f09b6647518adcfbf484da
@@ -2,6 +2,73 @@
2
2
 
3
3
  Notable changes to Apisonator will be tracked in this document.
4
4
 
5
+ ## 3.2.1 - 2021-01-22
6
+
7
+ ### Fixed
8
+
9
+ - Reports of 0 hits no longer generate unnecessary stats keys in Redis
10
+ ([#247](https://github.com/3scale/apisonator/pull/247)).
11
+
12
+ ## 3.2.0 - 2021-01-19
13
+
14
+ ### Added
15
+
16
+ - New endpoint in the internal API to get the provider key for a given (token,
17
+ service_id) pair ([#243](https://github.com/3scale/apisonator/pull/243)).
18
+
19
+ ### Changed
20
+
21
+ - The config file used when running in a Docker image now parses "1" and "true"
22
+ (case-insensitive) as true
23
+ ([#245](https://github.com/3scale/apisonator/pull/245)).
24
+
25
+ ### Fixed
26
+
27
+ - Fixed some metrics of the internal API that were not being counted
28
+ correctly([#244](https://github.com/3scale/apisonator/pull/244)).
29
+
30
+
31
+ ## 3.1.0 - 2020-10-14
32
+
33
+ ### Added
34
+
35
+ - Prometheus metrics for the internal API
36
+ ([#236](https://github.com/3scale/apisonator/pull/236)).
37
+ - Docs with a detailed explanation about how counter updates are performed
38
+ ([#239](https://github.com/3scale/apisonator/pull/239)).
39
+
40
+ ### Changed
41
+
42
+ - NotifyJobs are run only when the service ID is explicitly defined
43
+ ([#238](https://github.com/3scale/apisonator/pull/238)).
44
+
45
+ ### Fixed
46
+
47
+ - Fixed corner case that raised "TransactionTimestampNotWithinRange" in notify
48
+ jobs ([#235](https://github.com/3scale/apisonator/pull/235)).
49
+
50
+
51
+ ## 3.0.1.1 - 2020-07-28
52
+
53
+ ### Changed
54
+
55
+ - Updated json gem to v2.3.1
56
+ ([#232](https://github.com/3scale/apisonator/pull/232)).
57
+
58
+ ## 3.0.1 - 2020-07-14
59
+
60
+ ### Fixed
61
+
62
+ - The Prometheus counter of "5xx" errors has been fixed
63
+ ([#230](https://github.com/3scale/apisonator/pull/230)).
64
+
65
+ ### Changed
66
+
67
+ - Gem updates: rack to v2.1.4
68
+ ([#228](https://github.com/3scale/apisonator/pull/228)) and async-redis to
69
+ v0.5.0 ([#229](https://github.com/3scale/apisonator/pull/229)).
70
+
71
+
5
72
  ## 3.0.0 - 2020-06-19
6
73
 
7
74
  ### Removed
@@ -53,13 +53,13 @@ gem 'rake', '~> 13.0'
53
53
  gem 'builder', '= 3.2.3'
54
54
  # Use a patched resque to allow reusing their Airbrake Failure class
55
55
  gem 'resque', git: 'https://github.com/3scale/resque', branch: '3scale'
56
- gem 'rack', '~> 2.0.8'
56
+ gem 'rack', '~> 2.1.4'
57
57
  gem 'sinatra', '~> 2.0.3'
58
58
  gem 'sinatra-contrib', '~> 2.0.3'
59
59
  # Optional external error logging services
60
60
  gem 'bugsnag', '~> 6', require: nil
61
61
  gem 'yabeda-prometheus', '~> 0.5.0'
62
- gem 'async-redis', '~> 0.4.1'
62
+ gem 'async-redis', '~> 0.5'
63
63
  gem 'falcon', '~> 0.35'
64
64
 
65
65
  # Use a patched redis-rb that fixes an issue when trying to connect with
@@ -35,7 +35,7 @@ GIT
35
35
  PATH
36
36
  remote: .
37
37
  specs:
38
- apisonator (3.0.0)
38
+ apisonator (3.2.1)
39
39
 
40
40
  GEM
41
41
  remote: https://rubygems.org/
@@ -66,14 +66,15 @@ GEM
66
66
  async-http-cache (0.1.5)
67
67
  async-http
68
68
  protocol-http (~> 0.14)
69
- async-io (1.27.5)
69
+ async-io (1.27.7)
70
70
  async (~> 1.14)
71
71
  async-pool (0.2.0)
72
72
  async (~> 1.8)
73
- async-redis (0.4.1)
73
+ async-redis (0.5.0)
74
74
  async (~> 1.8)
75
75
  async-io (~> 1.10)
76
- protocol-redis (~> 0.2.0)
76
+ async-pool (~> 0.2)
77
+ protocol-redis (~> 0.5.0)
77
78
  async-rspec (1.13.0)
78
79
  rspec (~> 3.0)
79
80
  rspec-files (~> 1.0)
@@ -118,7 +119,7 @@ GEM
118
119
  i18n (1.8.2)
119
120
  concurrent-ruby (~> 1.0)
120
121
  jmespath (1.3.1)
121
- json (2.1.0)
122
+ json (2.3.1)
122
123
  license_finder (5.9.2)
123
124
  bundler
124
125
  rubyzip
@@ -161,7 +162,7 @@ GEM
161
162
  protocol-http2 (0.11.6)
162
163
  protocol-hpack (~> 1.4)
163
164
  protocol-http (~> 0.15)
164
- protocol-redis (0.2.0)
165
+ protocol-redis (0.5.0)
165
166
  pry (0.11.3)
166
167
  coderay (~> 1.1.0)
167
168
  method_source (~> 0.9.0)
@@ -171,7 +172,7 @@ GEM
171
172
  pry-doc (0.11.1)
172
173
  pry (~> 0.9)
173
174
  yard (~> 0.9)
174
- rack (2.0.9)
175
+ rack (2.1.4)
175
176
  rack-protection (2.0.3)
176
177
  rack
177
178
  rack-test (0.8.2)
@@ -266,7 +267,7 @@ PLATFORMS
266
267
  DEPENDENCIES
267
268
  airbrake (= 4.3.1)
268
269
  apisonator!
269
- async-redis (~> 0.4.1)
270
+ async-redis (~> 0.5)
270
271
  async-rspec
271
272
  aws-sdk (= 2.4.2)
272
273
  benchmark-ips (~> 2.7.2)
@@ -286,7 +287,7 @@ DEPENDENCIES
286
287
  pry-byebug (~> 3.5.1)
287
288
  pry-doc (~> 0.11.1)
288
289
  puma!
289
- rack (~> 2.0.8)
290
+ rack (~> 2.1.4)
290
291
  rack-test (~> 0.8.2)
291
292
  rake (~> 13.0)
292
293
  redis!
@@ -35,7 +35,7 @@ GIT
35
35
  PATH
36
36
  remote: .
37
37
  specs:
38
- apisonator (3.0.0)
38
+ apisonator (3.2.1)
39
39
 
40
40
  GEM
41
41
  remote: https://rubygems.org/
@@ -63,14 +63,15 @@ GEM
63
63
  async-http-cache (0.1.5)
64
64
  async-http
65
65
  protocol-http (~> 0.14)
66
- async-io (1.27.5)
66
+ async-io (1.27.7)
67
67
  async (~> 1.14)
68
68
  async-pool (0.2.0)
69
69
  async (~> 1.8)
70
- async-redis (0.4.1)
70
+ async-redis (0.5.0)
71
71
  async (~> 1.8)
72
72
  async-io (~> 1.10)
73
- protocol-redis (~> 0.2.0)
73
+ async-pool (~> 0.2)
74
+ protocol-redis (~> 0.5.0)
74
75
  async-rspec (1.13.0)
75
76
  rspec (~> 3.0)
76
77
  rspec-files (~> 1.0)
@@ -107,7 +108,7 @@ GEM
107
108
  hiredis (0.6.3)
108
109
  i18n (1.8.2)
109
110
  concurrent-ruby (~> 1.0)
110
- json (2.1.0)
111
+ json (2.3.1)
111
112
  license_finder (5.9.2)
112
113
  bundler
113
114
  rubyzip
@@ -149,7 +150,7 @@ GEM
149
150
  protocol-http2 (0.11.6)
150
151
  protocol-hpack (~> 1.4)
151
152
  protocol-http (~> 0.15)
152
- protocol-redis (0.2.0)
153
+ protocol-redis (0.5.0)
153
154
  pry (0.11.3)
154
155
  coderay (~> 1.1.0)
155
156
  method_source (~> 0.9.0)
@@ -159,7 +160,7 @@ GEM
159
160
  pry-doc (0.11.1)
160
161
  pry (~> 0.9)
161
162
  yard (~> 0.9)
162
- rack (2.0.9)
163
+ rack (2.1.4)
163
164
  rack-protection (2.0.3)
164
165
  rack
165
166
  rack-test (0.8.2)
@@ -249,7 +250,7 @@ PLATFORMS
249
250
 
250
251
  DEPENDENCIES
251
252
  apisonator!
252
- async-redis (~> 0.4.1)
253
+ async-redis (~> 0.5)
253
254
  async-rspec
254
255
  benchmark-ips (~> 2.7.2)
255
256
  bugsnag (~> 6)
@@ -267,7 +268,7 @@ DEPENDENCIES
267
268
  pry-byebug (~> 3.5.1)
268
269
  pry-doc (~> 0.11.1)
269
270
  puma!
270
- rack (~> 2.0.8)
271
+ rack (~> 2.1.4)
271
272
  rack-test (~> 0.8.2)
272
273
  rake (~> 13.0)
273
274
  redis!
@@ -7,6 +7,14 @@ module ThreeScale
7
7
  ServiceToken.exists?(token, service_id) ? 200 : 404
8
8
  end
9
9
 
10
+ get '/:token/:service_id/provider_key' do |token, service_id|
11
+ if ServiceToken.exists?(token, service_id)
12
+ { status: :found, provider_key: Service.provider_key_for(service_id) }.to_json
13
+ else
14
+ respond_with_404('token/service combination not found'.freeze)
15
+ end
16
+ end
17
+
10
18
  post '/' do
11
19
  check_tokens_param!
12
20
 
@@ -1,6 +1,7 @@
1
1
  require '3scale/backend/configuration/loader'
2
2
  require '3scale/backend/environment'
3
3
  require '3scale/backend/configurable'
4
+ require '3scale/backend/errors'
4
5
 
5
6
  module ThreeScale
6
7
  module Backend
@@ -77,9 +78,6 @@ module ThreeScale
77
78
  master_metrics = [:transactions, :transactions_authorize]
78
79
  config.master.metrics = Struct.new(*master_metrics).new
79
80
 
80
- # Default config
81
- config.master_service_id = 1
82
-
83
81
  # This setting controls whether the listener can create event buckets in
84
82
  # Redis. We do not want all the listeners creating buckets yet, as we do
85
83
  # not know exactly the rate at which we can send events to Kinesis
@@ -4,14 +4,36 @@ require 'rack'
4
4
  module ThreeScale
5
5
  module Backend
6
6
  class ListenerMetrics
7
- REQUEST_TYPES = {
7
+ AUTH_AND_REPORT_REQUEST_TYPES = {
8
8
  '/transactions/authorize.xml' => 'authorize',
9
9
  '/transactions/oauth_authorize.xml' => 'authorize_oauth',
10
10
  '/transactions/authrep.xml' => 'authrep',
11
11
  '/transactions/oauth_authrep.xml' => 'authrep_oauth',
12
12
  '/transactions.xml' => 'report'
13
13
  }
14
- private_constant :REQUEST_TYPES
14
+ private_constant :AUTH_AND_REPORT_REQUEST_TYPES
15
+
16
+ # Only the first match is taken into account, that's why for example,
17
+ # "/\/services\/.*\/stats/" needs to appear before "/\/services/"
18
+ INTERNAL_API_PATHS = [
19
+ [/\/services\/.*\/alert_limits/, 'alerts'.freeze],
20
+ [/\/services\/.*\/applications\/.*\/keys/, 'application_keys'.freeze],
21
+ [/\/services\/.*\/applications\/.*\/referrer_filters/, 'application_referrer_filters'.freeze],
22
+ [/\/services\/.*\/applications\/.*\/utilization/, 'utilization'.freeze],
23
+ [/\/services\/.*\/applications/, 'applications'.freeze],
24
+ [/\/services\/.*\/errors/, 'errors'.freeze],
25
+ [/\/events/, 'events'.freeze],
26
+ [/\/services\/.*\/metrics/, 'metrics'.freeze],
27
+ [/\/service_tokens/, 'service_tokens'.freeze],
28
+ [/\/services\/.*\/stats/, 'stats'.freeze],
29
+ [/\/services\/.*\/plans\/.*\/usagelimits/, 'usage_limits'.freeze],
30
+ [/\/services/, 'services'.freeze],
31
+ ].freeze
32
+ private_constant :INTERNAL_API_PATHS
33
+
34
+ # Most requests will be under 100ms, so use a higher granularity from there
35
+ TIME_BUCKETS = [0.01, 0.02, 0.03, 0.04, 0.05, 0.06, 0.07, 0.08, 0.09, 0.1, 0.25, 0.5, 0.75, 1]
36
+ private_constant :TIME_BUCKETS
15
37
 
16
38
  class << self
17
39
  ERRORS_4XX_TO_TRACK = Set[403, 404, 409].freeze
@@ -27,9 +49,12 @@ module ThreeScale
27
49
  end
28
50
 
29
51
  def report_resp_code(path, resp_code)
30
- Yabeda.apisonator_listener.response_codes.increment(
52
+ req_type = req_type(path)
53
+ prometheus_group = prometheus_group(req_type)
54
+
55
+ Yabeda.send(prometheus_group).response_codes.increment(
31
56
  {
32
- request_type: REQUEST_TYPES[path],
57
+ request_type: req_type,
33
58
  resp_code: code_group(resp_code)
34
59
  },
35
60
  by: 1
@@ -37,8 +62,11 @@ module ThreeScale
37
62
  end
38
63
 
39
64
  def report_response_time(path, request_time)
40
- Yabeda.apisonator_listener.response_times.measure(
41
- { request_type: REQUEST_TYPES[path] },
65
+ req_type = req_type(path)
66
+ prometheus_group = prometheus_group(req_type)
67
+
68
+ Yabeda.send(prometheus_group).response_times.measure(
69
+ { request_type: req_type },
42
70
  request_time
43
71
  )
44
72
  end
@@ -69,8 +97,21 @@ module ThreeScale
69
97
  comment 'Response times'
70
98
  unit :seconds
71
99
  tags %i[request_type]
72
- # Most requests will be under 100ms, so use a higher granularity from there
73
- buckets [0.01, 0.02, 0.03, 0.04, 0.05, 0.06, 0.07, 0.08, 0.09, 0.1, 0.25, 0.5, 0.75, 1]
100
+ buckets TIME_BUCKETS
101
+ end
102
+ end
103
+
104
+ group :apisonator_listener_internal_api do
105
+ counter :response_codes do
106
+ comment 'Response codes'
107
+ tags %i[request_type resp_code]
108
+ end
109
+
110
+ histogram :response_times do
111
+ comment 'Response times'
112
+ unit :seconds
113
+ tags %i[request_type]
114
+ buckets TIME_BUCKETS
74
115
  end
75
116
  end
76
117
  end
@@ -93,6 +134,24 @@ module ThreeScale
93
134
  'unknown'.freeze
94
135
  end
95
136
  end
137
+
138
+ def req_type(path)
139
+ AUTH_AND_REPORT_REQUEST_TYPES[path] || internal_api_req_type(path)
140
+ end
141
+
142
+ def internal_api_req_type(path)
143
+ (_regex, type) = INTERNAL_API_PATHS.find { |(regex, _)| regex.match path }
144
+ type
145
+ end
146
+
147
+ # Returns the group as defined in .define_metrics
148
+ def prometheus_group(request_type)
149
+ if AUTH_AND_REPORT_REQUEST_TYPES.values.include? request_type
150
+ :apisonator_listener
151
+ else
152
+ :apisonator_listener_internal_api
153
+ end
154
+ end
96
155
  end
97
156
  end
98
157
  end
@@ -8,7 +8,15 @@ module ThreeScale
8
8
 
9
9
  def call(env)
10
10
  began_at = Time.now.getutc
11
- status, header, body = @app.call(env)
11
+
12
+ begin
13
+ status, header, body = @app.call(env)
14
+ rescue Exception => e
15
+ ListenerMetrics.report_resp_code(env['REQUEST_PATH'], 500)
16
+ ListenerMetrics.report_response_time(env['REQUEST_PATH'], Time.now - began_at)
17
+ raise e
18
+ end
19
+
12
20
  ListenerMetrics.report_resp_code(env['REQUEST_PATH'], status)
13
21
  ListenerMetrics.report_response_time(env['REQUEST_PATH'], Time.now - began_at)
14
22
  [status, header, body]
@@ -47,7 +47,7 @@ module ThreeScale
47
47
 
48
48
  endpoint = Async::IO::Endpoint.tcp(host, port)
49
49
  @redis_async = Async::Redis::Client.new(
50
- endpoint, connection_limit: opts[:max_connections]
50
+ endpoint, limit: opts[:max_connections]
51
51
  )
52
52
  @building_pipeline = false
53
53
  end
@@ -20,8 +20,14 @@ module ThreeScale
20
20
  def report(provider_key, service_id, transactions, context_info = {})
21
21
  service = Service.load_with_provider_key!(service_id, provider_key)
22
22
 
23
- report_enqueue(service.id, transactions, context_info)
24
- notify_report(provider_key, transactions.size)
23
+ # A usage of 0 does not affect rate-limits or stats, so we do not need
24
+ # to report it.
25
+ filtered_transactions = filter_usages_with_0(transactions.clone)
26
+
27
+ return if filtered_transactions.empty?
28
+
29
+ report_enqueue(service.id, filtered_transactions, context_info)
30
+ notify_report(provider_key, filtered_transactions.size)
25
31
  end
26
32
 
27
33
  def authorize(provider_key, params, context_info = {})
@@ -137,9 +143,17 @@ module ThreeScale
137
143
 
138
144
  usage = params[:usage]
139
145
 
140
- if (usage || params[:log]) && status.authorized?
146
+ filtered_usage = filter_metrics_without_inc(usage.clone) if usage
147
+
148
+ if ((filtered_usage && !filtered_usage.empty?) || params[:log]) && status.authorized?
141
149
  application_id = status.application.id
142
- report_enqueue(status.service_id, { 0 => {"app_id" => application_id, "usage" => usage, "log" => params[:log] } }, request: { extensions: request_info[:extensions] })
150
+
151
+ report_enqueue(
152
+ status.service_id,
153
+ { 0 => {"app_id" => application_id, "usage" => filtered_usage, "log" => params[:log] } },
154
+ request: { extensions: request_info[:extensions] }
155
+ )
156
+
143
157
  notify_authrep(provider_key, usage ? 1 : 0)
144
158
  else
145
159
  notify_authorize(provider_key)
@@ -182,6 +196,19 @@ module ThreeScale
182
196
  end
183
197
  end
184
198
 
199
+ def filter_usages_with_0(transactions)
200
+ # There are plenty of existing tests using both a string and a symbol
201
+ # when accessing the usage.
202
+ transactions.delete_if do |_idx, tx|
203
+ (usage = tx['usage'.freeze] || tx[:usage]) or next
204
+ filter_metrics_without_inc(usage).empty?
205
+ end
206
+ end
207
+
208
+ def filter_metrics_without_inc(usage)
209
+ usage.delete_if { |_metric, delta| delta.to_s == '0'.freeze }
210
+ end
211
+
185
212
  def storage
186
213
  Storage.instance
187
214
  end
@@ -30,9 +30,13 @@ module ThreeScale
30
30
  end
31
31
 
32
32
  def notify(provider_key, usage)
33
- # batch several notifications together so that we can process just one
33
+ # We need the master service ID to report its metrics. If it's not
34
+ # set, we don't need to notify anything.
35
+ # Batch several notifications together so that we can process just one
34
36
  # job for a group of them.
35
- notify_batch(provider_key, usage)
37
+ unless configuration.master_service_id.to_s.empty?
38
+ notify_batch(provider_key, usage)
39
+ end
36
40
  end
37
41
 
38
42
  def notify_batch(provider_key, usage)
@@ -7,8 +7,6 @@ module ThreeScale
7
7
  extend Configurable
8
8
  @queue = :main
9
9
 
10
- InvalidMasterServiceId = Class.new(ThreeScale::Backend::Error)
11
-
12
10
  class << self
13
11
  def perform_logged(provider_key, usage, timestamp, _enqueue_time)
14
12
  application_id = Application.load_id_by_key(master_service_id, provider_key)
@@ -16,12 +14,42 @@ module ThreeScale
16
14
  if application_id && Application.exists?(master_service_id, application_id)
17
15
  master_metrics = Metric.load_all(master_service_id)
18
16
 
19
- ProcessJob.perform([{
20
- service_id: master_service_id,
21
- application_id: application_id,
22
- timestamp: timestamp,
23
- usage: master_metrics.process_usage(usage)
24
- }])
17
+ begin
18
+ ProcessJob.perform([{
19
+ service_id: master_service_id,
20
+ application_id: application_id,
21
+ timestamp: timestamp,
22
+ usage: master_metrics.process_usage(usage)
23
+ }])
24
+ rescue MetricInvalid => e
25
+ # This happens when the master account in Porta does not have
26
+ # the notify metrics defined (by default "transactions" and
27
+ # "transactions/authorize"). These metrics need to be created in
28
+ # Porta, Apisonator does not have a way to guarantee that
29
+ # they're defined.
30
+ # Notice that this rescue prevents the job from being retried.
31
+ # Apisonator can't know when the metrics will be created (if
32
+ # ever) so it's better to log the error rather than retrying
33
+ # these jobs for an undefined period of time.
34
+ Worker.logger.notify(e)
35
+ return [false, "#{e}"]
36
+ rescue TransactionTimestampNotWithinRange => e
37
+ # This is very unlikely to happen. The timestamps in a notify
38
+ # job are not set by users, they are set by the listeners. If
39
+ # this error happens it might mean that:
40
+ # a) The worker started processing this job way after the
41
+ # listener produced it. This can happen for example if we make
42
+ # some requests to a listener with no workers. The listeners
43
+ # will enqueue some notify jobs. If we start a worker hours
44
+ # later, we might see this error.
45
+ # b) There's some kind of clock skew issue.
46
+ # c) There's a bug.
47
+ #
48
+ # We can't raise here, because then, the job will be retried,
49
+ # but it's going to fail always if it has an old timestamp.
50
+ Worker.logger.notify(e)
51
+ return [false, "#{provider_key} #{application_id} #{e}"]
52
+ end
25
53
  end
26
54
  [true, "#{provider_key} #{application_id || '--'}"]
27
55
  end
@@ -29,15 +57,7 @@ module ThreeScale
29
57
  private
30
58
 
31
59
  def master_service_id
32
- value = configuration.master_service_id
33
-
34
- unless value
35
- raise InvalidMasterServiceId,
36
- "Can't find master service id. Make sure the \"master_service_id\" "\
37
- 'configuration value is set correctly'
38
- end
39
-
40
- value.to_s
60
+ configuration.master_service_id.to_s
41
61
  end
42
62
  end
43
63
  end
@@ -1,5 +1,5 @@
1
1
  module ThreeScale
2
2
  module Backend
3
- VERSION = '3.0.0'
3
+ VERSION = '3.2.1'
4
4
  end
5
5
  end
@@ -23,7 +23,7 @@
23
23
  </dependency>
24
24
  <dependency>
25
25
  <packageName>apisonator</packageName>
26
- <version>3.0.0</version>
26
+ <version>3.2.1</version>
27
27
  <licenses>
28
28
  <license>
29
29
  <name>Apache 2.0</name>
@@ -73,7 +73,7 @@
73
73
  </dependency>
74
74
  <dependency>
75
75
  <packageName>async-io</packageName>
76
- <version>1.27.5</version>
76
+ <version>1.27.7</version>
77
77
  <licenses>
78
78
  <license>
79
79
  <name>MIT</name>
@@ -93,7 +93,7 @@
93
93
  </dependency>
94
94
  <dependency>
95
95
  <packageName>async-redis</packageName>
96
- <version>0.4.1</version>
96
+ <version>0.5.0</version>
97
97
  <licenses>
98
98
  <license>
99
99
  <name>MIT</name>
@@ -371,7 +371,7 @@
371
371
  </dependency>
372
372
  <dependency>
373
373
  <packageName>json</packageName>
374
- <version>2.1.0</version>
374
+ <version>2.3.1</version>
375
375
  <licenses>
376
376
  <license>
377
377
  <name>ruby</name>
@@ -669,7 +669,7 @@
669
669
  </dependency>
670
670
  <dependency>
671
671
  <packageName>protocol-redis</packageName>
672
- <version>0.2.0</version>
672
+ <version>0.5.0</version>
673
673
  <licenses>
674
674
  <license>
675
675
  <name>MIT</name>
@@ -719,7 +719,7 @@
719
719
  </dependency>
720
720
  <dependency>
721
721
  <packageName>rack</packageName>
722
- <version>2.0.9</version>
722
+ <version>2.1.4</version>
723
723
  <licenses>
724
724
  <license>
725
725
  <name>MIT</name>
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: apisonator
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.0.0
4
+ version: 3.2.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Adam Ciganek
@@ -16,7 +16,7 @@ authors:
16
16
  autorequire:
17
17
  bindir: bin
18
18
  cert_chain: []
19
- date: 2020-06-19 00:00:00.000000000 Z
19
+ date: 2021-01-22 00:00:00.000000000 Z
20
20
  dependencies: []
21
21
  description: This gem provides a daemon that handles authorization and reporting of
22
22
  web services managed by 3scale.