restforce 5.1.1 → 5.2.3

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 68aba674731ec407d63a766c8bcf13a6a243e757e89b32c8bed07c07a2ee2a9e
4
- data.tar.gz: 1529b415da1c3d34ff477aea87116d147d5e2bd3e74ebde236ef9292545fad54
3
+ metadata.gz: 1a41bb3b7f6f9c7fc06a71266e685e82afae4d6e291553159a6909ed29485553
4
+ data.tar.gz: b7e01b436eafbd7be80dc4210fce034ff8ae08b4920241c84999b252d34501d2
5
5
  SHA512:
6
- metadata.gz: 5fc24ced1a9e38b622040d0b51ea3cd3aa2d4afc994ee41a8825ee2038c1f7379c56c2a32044a938102fe47030f02183549bdd91837ffab88320d99af13d27c5
7
- data.tar.gz: 1a0be3c634cb0b9bcea1b38463b09e62e54ceee49b44e30e852e42c14c91761eff4cf8a6a786611682cb0ba309704d85243499c00358b6e411ded15e805f421e
6
+ metadata.gz: b465fc051f6199309d6bf7c18328b6765a8c08fb24daf28e978bd478602a2b6988dbd3578c3cc6562d2b5066666fdb9ddb64b4bd9a73fe9297d5dc3a073388ca
7
+ data.tar.gz: b1cc8939cb52563e39959bf2df3b27d91f64dba0fc7b5afd1d80fea47a4cdc55b5c921a9eaeef39ba97923037cd9ef0a873e3eed96dca0e50581f73d6ab66f06
data/.circleci/config.yml CHANGED
@@ -34,23 +34,28 @@ references:
34
34
  destination: test-results
35
35
 
36
36
  jobs:
37
+ build-ruby31:
38
+ docker:
39
+ - image: cimg/ruby:3.1
40
+ steps: *steps
37
41
  build-ruby30:
38
42
  docker:
39
- - image: circleci/ruby:3.0
43
+ - image: cimg/ruby:3.0
40
44
  steps: *steps
41
45
  build-ruby27:
42
46
  docker:
43
- - image: circleci/ruby:2.7
47
+ - image: cimg/ruby:2.7
44
48
  steps: *steps
45
49
  build-ruby26:
46
50
  docker:
47
- - image: circleci/ruby:2.6
51
+ - image: cimg/ruby:2.6
48
52
  steps: *steps
49
53
 
50
54
  workflows:
51
55
  version: 2
52
56
  tests:
53
57
  jobs:
58
+ - build-ruby31
54
59
  - build-ruby30
55
60
  - build-ruby27
56
61
  - build-ruby26
data/CHANGELOG.md CHANGED
@@ -1,3 +1,23 @@
1
+ # 5.2.3 (Jan 17, 2022)
2
+
3
+ * Add official support for Ruby 3.1 (@timrogers)
4
+ * Fix handling of responses from the Composite API (@robob27)
5
+ * Fix dependencies to correctly declare that the gem doesn't work with [faraday](https://github.com/lostisland/faraday) `v1.9.0` or later (@timrogers)
6
+
7
+ # 5.2.2 (Dec 16, 2021)
8
+
9
+ * Handle the `MALFORMED_SEARCH` error returned by Salesforce (@timrogers)
10
+
11
+ # 5.2.1 (Dec 8, 2021)
12
+
13
+ * Handle the `OPERATION_TOO_LARGE` error returned by Salesforce (@timrogers)
14
+ * Handle the `INVALID_SIGNUP_COUNTRY` error returned by Salesforce (@timrogers)
15
+
16
+ ## 5.2.0 (Oct 15, 2021)
17
+
18
+ * Add support for Salesforce's Composite API and Composite Batch API (@meenie, @amacdougall)
19
+ * Improve the performance of counting numbers of query results with `Restforce::Collection#count`, avoiding unnecessary API requests (@jhass)
20
+
1
21
  ## 5.1.1 (Oct 13, 2021)
2
22
 
3
23
  * Handle the `INVALID_REPLICATION_DATE` error returned by Salesforce (@michaelwnyc)
data/Gemfile CHANGED
@@ -11,7 +11,7 @@ gem 'rake'
11
11
  gem 'rspec', '~> 3.10.0'
12
12
  gem 'rspec-collection_matchers', '~> 1.2.0'
13
13
  gem 'rspec-its', '~> 1.3.0'
14
- gem 'rspec_junit_formatter', '~> 0.4.1'
15
- gem 'rubocop', '~> 1.22.1'
14
+ gem 'rspec_junit_formatter', '~> 0.5.1'
15
+ gem 'rubocop', '~> 1.24.1'
16
16
  gem 'simplecov', '~> 0.21.2'
17
17
  gem 'webmock', '~> 3.14.0'
data/README.md CHANGED
@@ -12,6 +12,8 @@ Features include:
12
12
  * Support for parent-to-child relationships.
13
13
  * Support for aggregate queries.
14
14
  * Support for the [Streaming API](#streaming)
15
+ * Support for the [Composite API](#composite-api)
16
+ * Support for the [Composite Batch API](#composite-batch-api)
15
17
  * Support for the GetUpdated API
16
18
  * Support for blob data types.
17
19
  * Support for GZIP compression.
@@ -25,7 +27,7 @@ Features include:
25
27
 
26
28
  Add this line to your application's Gemfile:
27
29
 
28
- gem 'restforce', '~> 5.1.1'
30
+ gem 'restforce', '~> 5.2.3'
29
31
 
30
32
  And then execute:
31
33
 
@@ -573,6 +575,52 @@ end
573
575
  Boom, you're now receiving push notifications when Accounts are
574
576
  created/updated.
575
577
 
578
+ #### Composite API
579
+
580
+ Restforce supports the [Composite API](https://developer.salesforce.com/docs/atlas.en-us.api_rest.meta/api_rest/resources_composite_composite.htm).
581
+ This feature permits the user to send a composite object—that is, a complex
582
+ object with nested children—in a single API call. Up to 25 requests may be
583
+ included in a single composite.
584
+
585
+ Note that `GET` is not yet implemented for this API.
586
+
587
+ ```ruby
588
+ # build up an array of requests:
589
+ requests << {
590
+ method: :update,
591
+ sobject: sobject, # e.g. "Contact"
592
+ reference_id: reference_id,
593
+ data: data
594
+ }
595
+
596
+ # send every 25 requests as a subrequest in a single composite call
597
+ requests.each_slice(25).map do |req_slice|
598
+ client.composite do |subrequest|
599
+ req_slice.each do |r|
600
+ subrequest.send *r.values
601
+ end
602
+ end
603
+ end
604
+
605
+ # note that we're using `map` to return an array of each responses to each
606
+ # composite call; 100 requests will produce 4 responses
607
+ ```
608
+
609
+ #### Composite Batch API
610
+
611
+ Restforce supports the [Composite Batch API](https://developer.salesforce.com/docs/atlas.en-us.api_rest.meta/api_rest/resources_composite_batch.htm).
612
+ This feature permits up to 25 subrequests in a single request, though each
613
+ subrequest counts against the API limit. On the other hand, it has fewer
614
+ limitations than the Composite API.
615
+
616
+ ```
617
+ client.batch do |subrequests|
618
+ subrequests.create('Object', name: 'test')
619
+ subrequests.update('Object', id: '123', name: 'test')
620
+ subrequests.destroy('Object', '123')
621
+ end
622
+ ```
623
+
576
624
  #### Replaying Events
577
625
 
578
626
  Since API version 37.0, Salesforce stores events for 24 hours and they can be
@@ -8,5 +8,6 @@ module Restforce
8
8
  include Restforce::Concerns::Caching
9
9
  include Restforce::Concerns::API
10
10
  include Restforce::Concerns::BatchAPI
11
+ include Restforce::Concerns::CompositeAPI
11
12
  end
12
13
  end
@@ -27,12 +27,26 @@ module Restforce
27
27
  @raw_page['records'].size
28
28
  end
29
29
 
30
- # Return the size of the Collection without making any additional requests.
30
+ # Return the number of items in the Collection without making any additional
31
+ # requests and going through all of the pages of results, one by one. Instead,
32
+ # we can rely on the total count of results which Salesforce returns.
31
33
  def size
32
34
  @raw_page['totalSize']
33
35
  end
34
36
  alias length size
35
37
 
38
+ def count(*args)
39
+ # By default, `Enumerable`'s `#count` uses `#each`, which means going through all
40
+ # of the pages of results, one by one. Instead, we can use `#size` which we have
41
+ # already overridden to work in a smarter, more efficient way. This only works for
42
+ # the simple version of `#count` with no arguments. When called with an argument or
43
+ # a block, you need to know what the items in the collection actually are, so we
44
+ # call `super` and end up iterating through each item in the collection.
45
+ return size unless block_given? || !args.empty?
46
+
47
+ super
48
+ end
49
+
36
50
  # Returns true if the size of the Collection is zero.
37
51
  def empty?
38
52
  size.zero?
@@ -61,9 +61,9 @@ module Restforce
61
61
  def initialize(opts = {})
62
62
  raise ArgumentError, 'Please specify a hash of options' unless opts.is_a?(Hash)
63
63
 
64
- @options = Restforce.configuration.options.map do |option|
64
+ @options = Restforce.configuration.options.to_h do |option|
65
65
  [option, Restforce.configuration.send(option)]
66
- end.to_h
66
+ end
67
67
 
68
68
  @options.merge! opts
69
69
  yield builder if block_given?
@@ -0,0 +1,104 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'restforce/concerns/verbs'
4
+
5
+ module Restforce
6
+ module Concerns
7
+ module CompositeAPI
8
+ extend Restforce::Concerns::Verbs
9
+
10
+ define_verbs :post
11
+
12
+ def composite(all_or_none: false, collate_subrequests: false)
13
+ subrequests = Subrequests.new(options)
14
+ yield(subrequests)
15
+
16
+ if subrequests.requests.length > 25
17
+ raise ArgumentError, 'Cannot have more than 25 subrequests.'
18
+ end
19
+
20
+ properties = {
21
+ compositeRequest: subrequests.requests,
22
+ allOrNone: all_or_none,
23
+ collateSubrequests: collate_subrequests
24
+ }
25
+ response = api_post('composite', properties.to_json)
26
+
27
+ results = response.body['compositeResponse']
28
+ has_errors = results.any? { |result| result['httpStatusCode'].digits.last == 4 }
29
+ if all_or_none && has_errors
30
+ last_error_index = results.rindex { |result| result['httpStatusCode'] != 412 }
31
+ last_error = results[last_error_index]
32
+ raise CompositeAPIError, last_error['body'][0]['errorCode']
33
+ end
34
+
35
+ results
36
+ end
37
+
38
+ def composite!(collate_subrequests: false, &block)
39
+ composite(all_or_none: true, collate_subrequests: collate_subrequests, &block)
40
+ end
41
+
42
+ class Subrequests
43
+ def initialize(options)
44
+ @options = options
45
+ @requests = []
46
+ end
47
+ attr_reader :options, :requests
48
+
49
+ def create(sobject, reference_id, attrs)
50
+ requests << {
51
+ method: 'POST',
52
+ url: composite_api_path(sobject),
53
+ body: attrs,
54
+ referenceId: reference_id
55
+ }
56
+ end
57
+
58
+ def update(sobject, reference_id, attrs)
59
+ id = attrs.fetch(attrs.keys.find { |k, _v| k.to_s.casecmp?('id') }, nil)
60
+ raise ArgumentError, 'Id field missing from attrs.' unless id
61
+
62
+ attrs_without_id = attrs.reject { |k, _v| k.to_s.casecmp?('id') }
63
+ requests << {
64
+ method: 'PATCH',
65
+ url: composite_api_path("#{sobject}/#{id}"),
66
+ body: attrs_without_id,
67
+ referenceId: reference_id
68
+ }
69
+ end
70
+
71
+ def destroy(sobject, reference_id, id)
72
+ requests << {
73
+ method: 'DELETE',
74
+ url: composite_api_path("#{sobject}/#{id}"),
75
+ referenceId: reference_id
76
+ }
77
+ end
78
+
79
+ def upsert(sobject, reference_id, ext_field, attrs)
80
+ raise ArgumentError, 'External id field missing.' unless ext_field
81
+
82
+ ext_id = attrs.fetch(attrs.keys.find do |k, _v|
83
+ k.to_s.casecmp?(ext_field.to_s)
84
+ end, nil)
85
+ raise ArgumentError, 'External id missing from attrs.' unless ext_id
86
+
87
+ attrs_without_ext_id = attrs.reject { |k, _v| k.to_s.casecmp?(ext_field) }
88
+ requests << {
89
+ method: 'PATCH',
90
+ url: composite_api_path("#{sobject}/#{ext_field}/#{ext_id}"),
91
+ body: attrs_without_ext_id,
92
+ referenceId: reference_id
93
+ }
94
+ end
95
+
96
+ private
97
+
98
+ def composite_api_path(path)
99
+ "/services/data/v#{options[:api_version]}/sobjects/#{path}"
100
+ end
101
+ end
102
+ end
103
+ end
104
+ end
@@ -245,6 +245,8 @@ module Restforce
245
245
 
246
246
  class InvalidSessionId < ResponseError; end
247
247
 
248
+ class InvalidSignupCountry < ResponseError; end
249
+
248
250
  class InvalidStatus < ResponseError; end
249
251
 
250
252
  class InvalidType < ResponseError; end
@@ -275,6 +277,8 @@ module Restforce
275
277
 
276
278
  class MalformedQuery < ResponseError; end
277
279
 
280
+ class MalformedSearch < ResponseError; end
281
+
278
282
  class ManagerNotDefined < ResponseError; end
279
283
 
280
284
  class MassmailRetryLimitExceeded < ResponseError; end
@@ -331,6 +335,8 @@ module Restforce
331
335
 
332
336
  class OpWithInvalidUserTypeException < ResponseError; end
333
337
 
338
+ class OperationTooLarge < ResponseError; end
339
+
334
340
  class OptedOutOfMassMail < ResponseError; end
335
341
 
336
342
  class PackageLicenseRequired < ResponseError; end
@@ -531,6 +537,7 @@ module Restforce
531
537
  "INVALID_REPLICATION_DATE" => InvalidReplicationDate,
532
538
  "INVALID_SAVE_AS_ACTIVITY_FLAG" => InvalidSaveAsActivityFlag,
533
539
  "INVALID_SESSION_ID" => InvalidSessionId,
540
+ "INVALID_SIGNUP_COUNTRY" => InvalidSignupCountry,
534
541
  "INVALID_STATUS" => InvalidStatus,
535
542
  "INVALID_TYPE" => InvalidType,
536
543
  "INVALID_TYPE_FOR_OPERATION" => InvalidTypeForOperation,
@@ -546,6 +553,7 @@ module Restforce
546
553
  "LOGIN_MUST_USE_SECURITY_TOKEN" => LoginMustUseSecurityToken,
547
554
  "MALFORMED_ID" => MalformedId,
548
555
  "MALFORMED_QUERY" => MalformedQuery,
556
+ "MALFORMED_SEARCH" => MalformedSearch,
549
557
  "MANAGER_NOT_DEFINED" => ManagerNotDefined,
550
558
  "MASSMAIL_RETRY_LIMIT_EXCEEDED" => MassmailRetryLimitExceeded,
551
559
  "MASS_MAIL_LIMIT_EXCEEDED" => MassMailLimitExceeded,
@@ -574,6 +582,7 @@ module Restforce
574
582
  "NUMBER_OUTSIDE_VALID_RANGE" => NumberOutsideValidRange,
575
583
  "NUM_HISTORY_FIELDS_BY_SOBJECT_EXCEEDED" => NumHistoryFieldsBySobjectExceeded,
576
584
  "OP_WITH_INVALID_USER_TYPE_EXCEPTION" => OpWithInvalidUserTypeException,
585
+ "OPERATION_TOO_LARGE" => OperationTooLarge,
577
586
  "OPTED_OUT_OF_MASS_MAIL" => OptedOutOfMassMail,
578
587
  "PACKAGE_LICENSE_REQUIRED" => PackageLicenseRequired,
579
588
  "PLATFORM_EVENT_ENCRYPTION_ERROR" => PlatformEventEncryptionError,
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Restforce
4
- VERSION = '5.1.1'
4
+ VERSION = '5.2.3'
5
5
  end
data/lib/restforce.rb CHANGED
@@ -32,6 +32,7 @@ module Restforce
32
32
  autoload :Base, 'restforce/concerns/base'
33
33
  autoload :API, 'restforce/concerns/api'
34
34
  autoload :BatchAPI, 'restforce/concerns/batch_api'
35
+ autoload :CompositeAPI, 'restforce/concerns/composite_api'
35
36
  end
36
37
 
37
38
  module Data
@@ -48,6 +49,7 @@ module Restforce
48
49
  UnauthorizedError = Class.new(Faraday::ClientError)
49
50
  APIVersionError = Class.new(Error)
50
51
  BatchAPIError = Class.new(Error)
52
+ CompositeAPIError = Class.new(Error)
51
53
 
52
54
  # Inherit from Faraday::ResourceNotFound for backwards-compatibility
53
55
  # Consumers of this library that rescue and handle Faraday::ResourceNotFound
data/restforce.gemspec CHANGED
@@ -19,13 +19,14 @@ Gem::Specification.new do |gem|
19
19
 
20
20
  gem.metadata = {
21
21
  'source_code_uri' => 'https://github.com/restforce/restforce',
22
- 'changelog_uri' => 'https://github.com/restforce/restforce/blob/master/CHANGELOG.md'
22
+ 'changelog_uri' => 'https://github.com/restforce/restforce/blob/master/CHANGELOG.md',
23
+ 'rubygems_mfa_required' => 'true'
23
24
  }
24
25
 
25
26
  gem.required_ruby_version = '>= 2.6'
26
27
 
27
- gem.add_dependency 'faraday', '<= 2.0', '>= 0.9.0'
28
+ gem.add_dependency 'faraday', '< 1.9.0', '>= 0.9.0'
28
29
  gem.add_dependency 'faraday_middleware', ['>= 0.8.8', '<= 2.0']
29
- gem.add_dependency 'hashie', '>= 1.2.0', '< 5.0'
30
+ gem.add_dependency 'hashie', '>= 1.2.0', '< 6.0'
30
31
  gem.add_dependency 'jwt', ['>= 1.5.6']
31
32
  end
@@ -0,0 +1,143 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ describe Restforce::Concerns::CompositeAPI do
6
+ let(:endpoint) { 'composite' }
7
+
8
+ before do
9
+ client.should_receive(:options).and_return(api_version: 38.0)
10
+ end
11
+
12
+ shared_examples_for 'composite requests' do
13
+ it '#create' do
14
+ client.
15
+ should_receive(:api_post).
16
+ with(endpoint, { compositeRequest: [
17
+ {
18
+ method: 'POST',
19
+ url: '/services/data/v38.0/sobjects/Object',
20
+ body: { name: 'test' },
21
+ referenceId: 'create_ref'
22
+ }
23
+ ], allOrNone: all_or_none, collateSubrequests: false }.to_json).
24
+ and_return(response)
25
+
26
+ client.send(method) do |subrequests|
27
+ subrequests.create('Object', 'create_ref', name: 'test')
28
+ end
29
+ end
30
+
31
+ it '#update' do
32
+ client.
33
+ should_receive(:api_post).
34
+ with(endpoint, { compositeRequest: [
35
+ {
36
+ method: 'PATCH',
37
+ url: '/services/data/v38.0/sobjects/Object/123',
38
+ body: { name: 'test' },
39
+ referenceId: 'update_ref'
40
+ }
41
+ ], allOrNone: all_or_none, collateSubrequests: false }.to_json).
42
+ and_return(response)
43
+
44
+ client.send(method) do |subrequests|
45
+ subrequests.update('Object', 'update_ref', id: '123', name: 'test')
46
+ end
47
+ end
48
+
49
+ it '#destroy' do
50
+ client.
51
+ should_receive(:api_post).
52
+ with(endpoint, { compositeRequest: [
53
+ {
54
+ method: 'DELETE',
55
+ url: '/services/data/v38.0/sobjects/Object/123',
56
+ referenceId: 'destroy_ref'
57
+ }
58
+ ], allOrNone: all_or_none, collateSubrequests: false }.to_json).
59
+ and_return(response)
60
+
61
+ client.send(method) do |subrequests|
62
+ subrequests.destroy('Object', 'destroy_ref', '123')
63
+ end
64
+ end
65
+
66
+ it '#upsert' do
67
+ client.
68
+ should_receive(:api_post).
69
+ with(endpoint, { compositeRequest: [
70
+ {
71
+ method: 'PATCH',
72
+ url: '/services/data/v38.0/sobjects/Object/extIdField__c/456',
73
+ body: { name: 'test' },
74
+ referenceId: 'upsert_ref'
75
+ }
76
+ ], allOrNone: all_or_none, collateSubrequests: false }.to_json).
77
+ and_return(response)
78
+
79
+ client.send(method) do |subrequests|
80
+ subrequests.upsert('Object', 'upsert_ref', 'extIdField__c',
81
+ extIdField__c: '456', name: 'test')
82
+ end
83
+ end
84
+
85
+ it 'multiple subrequests' do
86
+ client.
87
+ should_receive(:api_post).
88
+ with(endpoint, { compositeRequest: [
89
+ {
90
+ method: 'POST',
91
+ url: '/services/data/v38.0/sobjects/Object',
92
+ body: { name: 'test' },
93
+ referenceId: 'create_ref'
94
+ },
95
+ {
96
+ method: 'PATCH',
97
+ url: '/services/data/v38.0/sobjects/Object/123',
98
+ body: { name: 'test' },
99
+ referenceId: 'update_ref'
100
+ },
101
+ {
102
+ method: 'DELETE',
103
+ url: '/services/data/v38.0/sobjects/Object/123',
104
+ referenceId: 'destroy_ref'
105
+ }
106
+ ], allOrNone: all_or_none, collateSubrequests: false }.to_json).
107
+ and_return(response)
108
+
109
+ client.send(method) do |subrequests|
110
+ subrequests.create('Object', 'create_ref', name: 'test')
111
+ subrequests.update('Object', 'update_ref', id: '123', name: 'test')
112
+ subrequests.destroy('Object', 'destroy_ref', '123')
113
+ end
114
+ end
115
+
116
+ it 'fails if more than 25 requests' do
117
+ expect do
118
+ client.send(method) do |subrequests|
119
+ 26.times do |i|
120
+ subrequests.upsert('Object', "upsert_ref_#{i}", 'extIdField__c',
121
+ extIdField__c: '456', name: 'test')
122
+ end
123
+ end
124
+ end.to raise_error(ArgumentError)
125
+ end
126
+ end
127
+
128
+ describe '#composite' do
129
+ let(:method) { :composite }
130
+ let(:all_or_none) { false }
131
+ let(:response) { double('Faraday::Response', body: { 'compositeResponse' => [] }) }
132
+ it_behaves_like 'composite requests'
133
+ end
134
+
135
+ describe '#composite!' do
136
+ let(:method) { :composite! }
137
+ let(:all_or_none) { true }
138
+ let(:response) do
139
+ double('Faraday::Response', body: { 'compositeResponse' => [] })
140
+ end
141
+ it_behaves_like 'composite requests'
142
+ end
143
+ end
@@ -87,7 +87,7 @@ describe Restforce::Concerns::Streaming, event_machine: true do
87
87
  end
88
88
 
89
89
  it 'connects to the streaming api' do
90
- client.stub authenticate!: OpenStruct.new(access_token: 'secret2')
90
+ client.stub authenticate!: double(access_token: 'secret2')
91
91
  faye_double = double('Faye::Client')
92
92
  Faye::Client.
93
93
  should_receive(:new).
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: restforce
3
3
  version: !ruby/object:Gem::Version
4
- version: 5.1.1
4
+ version: 5.2.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tim Rogers
@@ -9,15 +9,15 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2021-10-13 00:00:00.000000000 Z
12
+ date: 2022-01-17 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: faraday
16
16
  requirement: !ruby/object:Gem::Requirement
17
17
  requirements:
18
- - - "<="
18
+ - - "<"
19
19
  - !ruby/object:Gem::Version
20
- version: '2.0'
20
+ version: 1.9.0
21
21
  - - ">="
22
22
  - !ruby/object:Gem::Version
23
23
  version: 0.9.0
@@ -25,9 +25,9 @@ dependencies:
25
25
  prerelease: false
26
26
  version_requirements: !ruby/object:Gem::Requirement
27
27
  requirements:
28
- - - "<="
28
+ - - "<"
29
29
  - !ruby/object:Gem::Version
30
- version: '2.0'
30
+ version: 1.9.0
31
31
  - - ">="
32
32
  - !ruby/object:Gem::Version
33
33
  version: 0.9.0
@@ -60,7 +60,7 @@ dependencies:
60
60
  version: 1.2.0
61
61
  - - "<"
62
62
  - !ruby/object:Gem::Version
63
- version: '5.0'
63
+ version: '6.0'
64
64
  type: :runtime
65
65
  prerelease: false
66
66
  version_requirements: !ruby/object:Gem::Requirement
@@ -70,7 +70,7 @@ dependencies:
70
70
  version: 1.2.0
71
71
  - - "<"
72
72
  - !ruby/object:Gem::Version
73
- version: '5.0'
73
+ version: '6.0'
74
74
  - !ruby/object:Gem::Dependency
75
75
  name: jwt
76
76
  requirement: !ruby/object:Gem::Requirement
@@ -121,6 +121,7 @@ files:
121
121
  - lib/restforce/concerns/batch_api.rb
122
122
  - lib/restforce/concerns/caching.rb
123
123
  - lib/restforce/concerns/canvas.rb
124
+ - lib/restforce/concerns/composite_api.rb
124
125
  - lib/restforce/concerns/connection.rb
125
126
  - lib/restforce/concerns/picklists.rb
126
127
  - lib/restforce/concerns/streaming.rb
@@ -209,6 +210,7 @@ files:
209
210
  - spec/unit/concerns/batch_api_spec.rb
210
211
  - spec/unit/concerns/caching_spec.rb
211
212
  - spec/unit/concerns/canvas_spec.rb
213
+ - spec/unit/concerns/composite_api_spec.rb
212
214
  - spec/unit/concerns/connection_spec.rb
213
215
  - spec/unit/concerns/streaming_spec.rb
214
216
  - spec/unit/config_spec.rb
@@ -236,6 +238,7 @@ licenses:
236
238
  metadata:
237
239
  source_code_uri: https://github.com/restforce/restforce
238
240
  changelog_uri: https://github.com/restforce/restforce/blob/master/CHANGELOG.md
241
+ rubygems_mfa_required: 'true'
239
242
  post_install_message:
240
243
  rdoc_options: []
241
244
  require_paths:
@@ -310,6 +313,7 @@ test_files:
310
313
  - spec/unit/concerns/batch_api_spec.rb
311
314
  - spec/unit/concerns/caching_spec.rb
312
315
  - spec/unit/concerns/canvas_spec.rb
316
+ - spec/unit/concerns/composite_api_spec.rb
313
317
  - spec/unit/concerns/connection_spec.rb
314
318
  - spec/unit/concerns/streaming_spec.rb
315
319
  - spec/unit/config_spec.rb