zendesk_api 2.0.1 → 3.0.0

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: 6d8920d00f8d7aed5156fa8cfd6999f03cfdf17396a3725af756dcc58f885c65
4
- data.tar.gz: 26255546558e7027ff19b01f342a60765f28f177b7bdc98b804aaced279e2400
3
+ metadata.gz: 046b08ad011057c7e045d3fef61ade1bb53bba9ca227af8e3dee1178314c19ba
4
+ data.tar.gz: 881955416b716f0443d5ac672f21553cc24fed908a5cd8c1c6d8fea4529c65f3
5
5
  SHA512:
6
- metadata.gz: f7fde8ccb0d63280da8aed88cda9966b95b0d239df25c52e944b3c742859654a6320ced0effcf29c424b0c543cda152ee51c166f8df312cf5775c07d617caf68
7
- data.tar.gz: 300330f41f85653aee3766ac5683b85c40f696c3b5d6d20ec3c9aabfb503bf275bd8c05f84a0a27d51038069053f3a1b0678cc41650948922cfdde01056a7b45
6
+ metadata.gz: 1c357b5f778dae331777582f195f040879573f113200acd30a1f852baaa64109baabd7f1e18045eb6e39c7ef14d692fd450dd18789faf78b322e1ba6e2ca0616
7
+ data.tar.gz: 0515f3c1cf1fe24372895052ad6d76094d185c2d4e2b565bf51f22225b058caca10caa86ebd8f447cca83e31cfb05f9b0ce11f9bcd53fa2f4a9b93b682dd5439
@@ -24,7 +24,7 @@ module ZendeskAPI
24
24
  # The top-level class that handles configuration and connection to the Zendesk API.
25
25
  # Can also be used as an accessor to resource collections.
26
26
  class Client
27
- GZIP_EXCEPTIONS = [:em_http, :httpclient]
27
+ GZIP_EXCEPTIONS = [:em_http, :httpclient, :httpx]
28
28
 
29
29
  # @return [Configuration] Config instance
30
30
  attr_reader :config
@@ -6,6 +6,8 @@ module ZendeskAPI
6
6
  # Represents a collection of resources. Lazily loaded, resources aren't
7
7
  # actually fetched until explicitly needed (e.g. #each, {#fetch}).
8
8
  class Collection
9
+ DEFAULT_PAGE_SIZE = 100
10
+
9
11
  include ZendeskAPI::Sideloading
10
12
 
11
13
  # Options passed in that are automatically converted from an array to a comma-separated list.
@@ -186,17 +188,8 @@ module ZendeskAPI
186
188
  elsif association && association.options.parent && association.options.parent.new_record?
187
189
  return (@resources = [])
188
190
  end
189
- path_query_link = (@query || path)
190
-
191
- @response = get_response(path_query_link)
192
-
193
- if path_query_link == "search/export"
194
- handle_cursor_response(@response.body)
195
- else
196
- handle_response(@response.body)
197
- end
198
191
 
199
- @resources
192
+ get_resources(@query || path)
200
193
  end
201
194
 
202
195
  def fetch(*args)
@@ -252,10 +245,12 @@ module ZendeskAPI
252
245
  # * If there is a next_page url cached, it executes a fetch on that url and returns the results.
253
246
  # * Otherwise, returns an empty array.
254
247
  def next
255
- if @options["page"]
248
+ if @options["page"] && !cbp_request?
256
249
  clear_cache
257
- @options["page"] += 1
250
+ @options["page"] = @options["page"].to_i + 1
258
251
  elsif (@query = @next_page)
252
+ # Send _only_ url param "?after=token" to get the next page
253
+ @options.page&.delete("before")
259
254
  fetch(true)
260
255
  else
261
256
  clear_cache
@@ -268,10 +263,12 @@ module ZendeskAPI
268
263
  # * If there is a prev_page url cached, it executes a fetch on that url and returns the results.
269
264
  # * Otherwise, returns an empty array.
270
265
  def prev
271
- if @options["page"] && @options["page"] > 1
266
+ if !cbp_request? && @options["page"].to_i > 1
272
267
  clear_cache
273
268
  @options["page"] -= 1
274
269
  elsif (@query = @prev_page)
270
+ # Send _only_ url param "?before=token" to get the prev page
271
+ @options.page&.delete("after")
275
272
  fetch(true)
276
273
  else
277
274
  clear_cache
@@ -327,21 +324,17 @@ module ZendeskAPI
327
324
  end
328
325
 
329
326
  def more_results?(response)
330
- response["meta"].present? && response["results"].present?
327
+ Helpers.present?(response["meta"]) && response["meta"]["has_more"]
331
328
  end
332
329
  alias_method :has_more_results?, :more_results? # For backward compatibility with 1.33.0 and 1.34.0
333
330
 
334
- def get_response_body(link)
335
- @client.connection.send("get", link).body
336
- end
337
-
338
331
  def get_next_page_data(original_response_body)
339
332
  link = original_response_body["links"]["next"]
340
-
333
+ result_key = @resource_class.model_key || "results"
341
334
  while link
342
- response = get_response_body(link)
335
+ response = @client.connection.send("get", link).body
343
336
 
344
- original_response_body["results"] = original_response_body["results"] + response["results"]
337
+ original_response_body[result_key] = original_response_body[result_key] + response[result_key]
345
338
 
346
339
  link = response["meta"]["has_more"] ? response["links"]["next"] : nil
347
340
  end
@@ -351,17 +344,69 @@ module ZendeskAPI
351
344
 
352
345
  private
353
346
 
347
+ def cbp_response?(body)
348
+ !!(body["meta"] && body["links"])
349
+ end
350
+
351
+ def cbp_request?
352
+ @options["page"].is_a?(Hash)
353
+ end
354
+
355
+ def intentional_obp_request?
356
+ Helpers.present?(@options["page"]) && !cbp_request?
357
+ end
358
+
359
+ def get_resources(path_query_link)
360
+ if intentional_obp_request?
361
+ warn "Offset Based Pagination will be deprecated soon"
362
+ elsif @next_page.nil?
363
+ @options_per_page_was = @options.delete("per_page")
364
+ # Default to CBP by using the page param as a map
365
+ @options.page = { size: (@options_per_page_was || DEFAULT_PAGE_SIZE) }
366
+ end
367
+
368
+ begin
369
+ # Try CBP first, unless the user explicitly asked for OBP
370
+ @response = get_response(path_query_link)
371
+ rescue ZendeskAPI::Error::NetworkError => e
372
+ raise e if intentional_obp_request?
373
+ # Fallback to OBP if CBP didn't work, using per_page param
374
+ @options.per_page = @options_per_page_was
375
+ @options.page = nil
376
+ @response = get_response(path_query_link)
377
+ end
378
+
379
+ # Keep pre-existing behaviour for search/export
380
+ if path_query_link == "search/export"
381
+ handle_search_export_response(@response.body)
382
+ else
383
+ handle_response(@response.body)
384
+ end
385
+ end
386
+
354
387
  def set_page_and_count(body)
355
388
  @count = (body["count"] || @resources.size).to_i
356
- @next_page, @prev_page = body["next_page"], body["previous_page"]
389
+ @next_page, @prev_page = page_links(body)
357
390
 
358
- if @next_page =~ /page=(\d+)/
391
+ if cbp_response?(body)
392
+ # We'll delete the one we don't need in #next or #prev
393
+ @options["page"]["after"] = body["meta"]["after_cursor"]
394
+ @options["page"]["before"] = body["meta"]["before_cursor"]
395
+ elsif @next_page =~ /page=(\d+)/
359
396
  @options["page"] = $1.to_i - 1
360
397
  elsif @prev_page =~ /page=(\d+)/
361
398
  @options["page"] = $1.to_i + 1
362
399
  end
363
400
  end
364
401
 
402
+ def page_links(body)
403
+ if body["meta"] && body["links"]
404
+ [body["links"]["next"], body["links"]["prev"]]
405
+ else
406
+ [body["next_page"], body["previous_page"]]
407
+ end
408
+ end
409
+
365
410
  def _all(start_page = @options["page"], bang = false, &block)
366
411
  raise(ArgumentError, "must pass a block") unless block
367
412
 
@@ -370,13 +415,7 @@ module ZendeskAPI
370
415
 
371
416
  while (bang ? fetch! : fetch)
372
417
  each do |resource|
373
- arguments = [resource, @options["page"] || 1]
374
-
375
- if block.arity >= 0
376
- arguments = arguments.take(block.arity)
377
- end
378
-
379
- block.call(*arguments)
418
+ block.call(resource, @options["page"] || 1)
380
419
  end
381
420
 
382
421
  last_page? ? break : self.next
@@ -422,7 +461,7 @@ module ZendeskAPI
422
461
 
423
462
  def get_response(path)
424
463
  @error = nil
425
- @response = @client.connection.send(@verb || "get", path) do |req|
464
+ @client.connection.send(@verb || "get", path) do |req|
426
465
  opts = @options.delete_if { |_, v| v.nil? }
427
466
 
428
467
  req.params.merge!(:include => @includes.join(",")) if @includes.any?
@@ -435,36 +474,30 @@ module ZendeskAPI
435
474
  end
436
475
  end
437
476
 
438
- def handle_cursor_response(response_body)
439
- unless response_body.is_a?(Hash)
440
- raise ZendeskAPI::Error::NetworkError, @response.env
441
- end
477
+ def handle_search_export_response(response_body)
478
+ assert_valid_response_body(response_body)
442
479
 
480
+ # Note this doesn't happen in #handle_response
443
481
  response_body = get_next_page_data(response_body) if more_results?(response_body)
444
482
 
445
483
  body = response_body.dup
446
484
  results = body.delete(@resource_class.model_key) || body.delete("results")
447
485
 
448
- unless results
449
- raise ZendeskAPI::Error::ClientError, "Expected #{@resource_class.model_key} or 'results' in response keys: #{body.keys.inspect}"
450
- end
486
+ assert_results(results, body)
451
487
 
452
488
  @resources = results.map do |res|
453
489
  wrap_resource(res)
454
490
  end
455
491
  end
456
492
 
493
+ # For both CBP and OBP
457
494
  def handle_response(response_body)
458
- unless response_body.is_a?(Hash)
459
- raise ZendeskAPI::Error::NetworkError, @response.env
460
- end
495
+ assert_valid_response_body(response_body)
461
496
 
462
497
  body = response_body.dup
463
498
  results = body.delete(@resource_class.model_key) || body.delete("results")
464
499
 
465
- unless results
466
- raise ZendeskAPI::Error::ClientError, "Expected #{@resource_class.model_key} or 'results' in response keys: #{body.keys.inspect}"
467
- end
500
+ assert_results(results, body)
468
501
 
469
502
  @resources = results.map do |res|
470
503
  wrap_resource(res)
@@ -472,6 +505,8 @@ module ZendeskAPI
472
505
 
473
506
  set_page_and_count(body)
474
507
  set_includes(@resources, @includes, body)
508
+
509
+ @resources
475
510
  end
476
511
 
477
512
  # Simplified Associations#wrap_resource
@@ -514,5 +549,16 @@ module ZendeskAPI
514
549
  def resource_methods
515
550
  @resource_methods ||= @resource_class.singleton_methods(false).map(&:to_sym)
516
551
  end
552
+
553
+ def assert_valid_response_body(response_body)
554
+ unless response_body.is_a?(Hash)
555
+ raise ZendeskAPI::Error::NetworkError, @response.env
556
+ end
557
+ end
558
+
559
+ def assert_results(results, body)
560
+ return if results
561
+ raise ZendeskAPI::Error::ClientError, "Expected #{@resource_class.model_key} or 'results' in response keys: #{body.keys.inspect}"
562
+ end
517
563
  end
518
564
  end
@@ -1,6 +1,10 @@
1
1
  module ZendeskAPI
2
2
  # @private
3
3
  module Helpers
4
+ def self.present?(value)
5
+ ![nil, false, "", " ", [], {}].include?(value)
6
+ end
7
+
4
8
  # From https://github.com/rubyworks/facets/blob/master/lib/core/facets/string/modulize.rb
5
9
  # Converts a string to module name representation.
6
10
  #
@@ -1,3 +1,3 @@
1
1
  module ZendeskAPI
2
- VERSION = "2.0.1"
2
+ VERSION = "3.0.0"
3
3
  end
data/lib/zendesk_api.rb CHANGED
@@ -3,5 +3,6 @@ module ZendeskAPI; end
3
3
  require 'faraday'
4
4
  require 'faraday/multipart'
5
5
 
6
+ require 'zendesk_api/helpers'
6
7
  require 'zendesk_api/core_ext/inflection'
7
8
  require 'zendesk_api/client'
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: zendesk_api
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.1
4
+ version: 3.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Steven Davidovitz
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2023-04-13 00:00:00.000000000 Z
12
+ date: 2023-06-22 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: faraday
@@ -152,9 +152,9 @@ licenses:
152
152
  - Apache-2.0
153
153
  metadata:
154
154
  bug_tracker_uri: https://github.com/zendesk/zendesk_api_client_rb/issues
155
- changelog_uri: https://github.com/zendesk/zendesk_api_client_rb/blob/v2.0.1/CHANGELOG.md
156
- documentation_uri: https://www.rubydoc.info/gems/zendesk_api/2.0.1
157
- source_code_uri: https://github.com/zendesk/zendesk_api_client_rb/tree/v2.0.1
155
+ changelog_uri: https://github.com/zendesk/zendesk_api_client_rb/blob/v3.0.0/CHANGELOG.md
156
+ documentation_uri: https://www.rubydoc.info/gems/zendesk_api/3.0.0
157
+ source_code_uri: https://github.com/zendesk/zendesk_api_client_rb/tree/v3.0.0
158
158
  wiki_uri: https://github.com/zendesk/zendesk_api_client_rb/wiki
159
159
  post_install_message:
160
160
  rdoc_options: []