restforce-db 2.7.0 → 3.0.0

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.
Files changed (17) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +12 -0
  3. data/lib/generators/templates/script +102 -3
  4. data/lib/restforce/db/instances/active_record.rb +20 -9
  5. data/lib/restforce/db/instances/salesforce.rb +0 -8
  6. data/lib/restforce/db/record_types/salesforce.rb +17 -5
  7. data/lib/restforce/db/version.rb +1 -1
  8. data/test/cassettes/Restforce_DB_Initializer/_run/given_an_existing_database_record/for_an_Always_strategy/populates_Salesforce_with_the_new_record.yml +56 -56
  9. data/test/cassettes/Restforce_DB_Model/given_a_database_model_which_includes_the_module/_force_sync_/given_an_unsynchronized_record_for_a_mapped_model/creates_a_matching_record_in_Salesforce.yml +49 -49
  10. data/test/cassettes/Restforce_DB_RecordTypes_Salesforce/_create_/creates_a_record_in_Salesforce_from_the_passed_database_record_s_attributes.yml +41 -41
  11. data/test/cassettes/Restforce_DB_RecordTypes_Salesforce/_create_/updates_the_database_record_with_the_Salesforce_record_s_ID.yml +41 -41
  12. data/test/cassettes/Restforce_DB_RecordTypes_Salesforce/_create_/when_a_Salesforce_record_already_exists_for_the_database_instance/uses_the_existing_record.yml +247 -0
  13. data/test/cassettes/Restforce_DB_Worker/a_race_condition_during_synchronization/does_not_change_the_user-entered_name_on_the_database_record.yml +106 -107
  14. data/test/cassettes/Restforce_DB_Worker/a_race_condition_during_synchronization/overrides_the_stale-but-more-recent_name_on_the_Salesforce.yml +114 -115
  15. data/test/lib/restforce/db/instances/active_record_test.rb +9 -2
  16. data/test/lib/restforce/db/record_types/salesforce_test.rb +14 -4
  17. metadata +3 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: c25a609455a6ec5468ec04c57c012cd8db246165
4
- data.tar.gz: 5ecc15d30bd49ebb8926e5e4aa11665311776b0a
3
+ metadata.gz: ed593fdcf73e145f3957db532c939650f7112b77
4
+ data.tar.gz: 2a20acce1c5b9d85e717d6dc33d9c1e85a1c392d
5
5
  SHA512:
6
- metadata.gz: 447d000eae9fa2c955a8dc1cead5458e5b40fcc7a40bac9bf43f920a02f174b5b085b38ed289c486feeee33af74ae4574f44665fee5d68dfe34b95da16cd96e6
7
- data.tar.gz: a69d6366987c9515962fcb2f465dd4c121744651eb5cf01291d2b7c1e7ad853c417ccc4006ad9aa5ea1f0fa00da95a15e958f18888ca94ea3bb974662e94367f
6
+ metadata.gz: 2f875a2b2f3f88717e2fd3ef74d842f25fc7b0bbc11726ee33ed3e91ed26c0744f28d647aa5d04c4a5bf548665f19fdc102462a84474ef694687d0df26d7ad4e
7
+ data.tar.gz: 0fab5908d5a1ae144f8563c4a27fb02f03004a932ac4044316d17f442047b0f170529ccf457ee6600e3a87fb5b0acdb606a18d56dd78804a9448bd54ee389c9d
data/README.md CHANGED
@@ -225,6 +225,18 @@ In the above example, `Dish__c` is a Salesforce object type which references the
225
225
 
226
226
  You may want to consult [the ActiveRecord documentation](http://apidock.com/rails/ActiveRecord/Associations/ClassMethods) for your specific use case.
227
227
 
228
+ ### Add an external ID to your Salesforce objects
229
+
230
+ If your application creates any objects that you want/need to propagate to Salesforce, you'll need to expose an external ID field named `SynchronizationId__c` on the Salesforce object. This external ID is used as a key for Salesforce's [upsert](https://developer.salesforce.com/docs/atlas.en-us.api_rest.meta/api_rest/dome_upsert.htm) API interaction, which allows Restforce::DB to avoid accidentally duplicating records via a less-safe non-idempotent POST to Salesforce.
231
+
232
+ The `restforce-db` executable has a handy mechanism for automating this:
233
+
234
+ $ ruby bin/restforce-db meta Restaurant__c Dish__c
235
+ # => ADDING SynchronizationId__c to Restaurant__c... DONE
236
+ # => ADDING SynchronizationId__c to Dish__c... DONE
237
+
238
+ NOTE: This script uses `bundler/inline` to get access to the `metaforce` gem at runtime. Due to some issues with Bundler's handling of inline gemfiles, the use of `ruby` versus `bundle exec` is intentional here.
239
+
228
240
  ### Seed your data
229
241
 
230
242
  To populate your database with existing information from Salesforce (or vice-versa), you _could_ manually update each of the records you care about, and expect the Restforce::DB daemon to automatically pick them up when it runs. However, for any record type you need/want to _fully_ synchronize, this can be a very tedious process.
@@ -1,6 +1,105 @@
1
1
  #!/usr/bin/env ruby
2
2
 
3
- require File.expand_path(File.join(File.dirname(__FILE__), "..", "config", "environment"))
4
- require "restforce/db/command"
3
+ if ARGV[0] != "meta"
4
+ require File.expand_path(File.join(File.dirname(__FILE__), "..", "config", "environment"))
5
+ require "restforce/db/command"
5
6
 
6
- Restforce::DB::Command.new(ARGV).daemonize
7
+ Restforce::DB::Command.new(ARGV).daemonize
8
+ elsif ARGV.length > 1 && !defined?(Bundler)
9
+
10
+ # MetadataInitializer exposes functionality to automatically add an
11
+ # external Synchronization ID to your Salesforce models.
12
+ class MetadataInitializer
13
+
14
+ # Public: Initialize a new MetadataInitializer.
15
+ #
16
+ # config_file - The path to a configuration file.
17
+ # models - An Array of String Salesforce model names.
18
+ def initialize(config_file, *models)
19
+ @models = models
20
+ @config = YAML.load_file(config_file)
21
+ end
22
+
23
+ # Public: Set up an external Synchronization ID for each specified
24
+ # Salesforce model.
25
+ #
26
+ # Returns nothing.
27
+ def setup
28
+ @models.each do |model|
29
+ print "ADDING SynchronizationId__c to #{model}... "
30
+ job = client.create(
31
+ :custom_field,
32
+ full_name: "#{model}.SynchronizationId__c",
33
+ description: "External Synchronization ID",
34
+ label: "Synchronization ID",
35
+ type: "Text",
36
+ external_id: true,
37
+ unique: true,
38
+ length: ENV["UUID_LENGTH"] || 255,
39
+ )
40
+
41
+ begin
42
+ job.on_complete { |_| puts "DONE" }.on_error { |_| puts "FAILED" }.perform
43
+ rescue Savon::SOAP::Fault => e
44
+ puts "\n(#{e.class}) #{e.message}\n#{e.backtrace.join("\n")}"
45
+ end
46
+ end
47
+ end
48
+
49
+ # Internal: Get a Metaforce client to process the custom field CRUD
50
+ # requests.
51
+ #
52
+ # Returns a Metaforce::Metadata:Client.
53
+ def client
54
+ @client ||= begin
55
+ Metaforce.configure do |configuration|
56
+ configuration.host = @config["client"]["host"]
57
+ configuration.log = false
58
+ end
59
+
60
+ options = {
61
+ username: @config["client"]["username"],
62
+ password: @config["client"]["password"],
63
+ security_token: @config["client"]["security_token"],
64
+ }
65
+
66
+ # Verify the login credentials
67
+ Metaforce.login(options)
68
+ Metaforce.new(options)
69
+ end
70
+ end
71
+
72
+ end
73
+
74
+ # NOTE: For whatever reason, bundler/inline's "install" functionality seems
75
+ # busted. We can work around it by just installing the gem ourselves, as a
76
+ # convenience to users.
77
+ unless `gem list metaforce -i` == "true\n"
78
+ system "gem install metaforce"
79
+ puts
80
+ end
81
+
82
+ # Suppress bundler output
83
+ require "stringio"
84
+ stdout, $stdout = $stdout, StringIO.new
85
+
86
+ require "bundler/inline"
87
+ require "yaml"
88
+
89
+ gemfile(true) do
90
+ source "https://rubygems.org"
91
+
92
+ # NOTE: Necessary to deal with a bad require in Metaforce
93
+ gem "activesupport", require: "active_support"
94
+ gem "metaforce"
95
+ end
96
+
97
+ $stdout = stdout
98
+
99
+ config_file = ENV["CONFIG"] || Pathname.new(Dir.pwd).join("config", "restforce-db.yml")
100
+ MetadataInitializer.new(config_file, *ARGV[1..-1]).setup
101
+ else
102
+ puts "The `meta` command doesn't work through `bundle exec`." if defined?(Bundler)
103
+ puts "You must supply at least one Salesforce model." if ARGV.length < 2
104
+ puts "Use the syntax `ruby bin/restforce-db meta <sobject> [<sobject>...]`"
105
+ end
@@ -14,23 +14,24 @@ module Restforce
14
14
  #
15
15
  # Returns a String.
16
16
  def id
17
- return "#{@record_type}::#{@record.id}" unless synced?
17
+ return uuid unless synced?
18
18
  @record.send(@mapping.lookup_column)
19
19
  end
20
20
 
21
- # Public: Get the time of the last update to this record.
21
+ # Public: Get a unique identifier for this record. This value should
22
+ # be consistent for the specific ActiveRecord object passed to this
23
+ # instance.
22
24
  #
23
- # Returns a Time-compatible object.
24
- def last_update
25
- @record.updated_at
25
+ # Returns nothing.
26
+ def uuid
27
+ "#{@record_type}::#{@record.id}"
26
28
  end
27
29
 
28
- # Public: Get the time of the last synchronization update to this
29
- # record.
30
+ # Public: Get the time of the last update to this record.
30
31
  #
31
32
  # Returns a Time-compatible object.
32
- def last_synchronize
33
- @record.synchronized_at
33
+ def last_update
34
+ @record.updated_at
34
35
  end
35
36
 
36
37
  # Public: Has this record been synced to a Salesforce record?
@@ -56,6 +57,16 @@ module Restforce
56
57
  super
57
58
  end
58
59
 
60
+ private
61
+
62
+ # Internal: Get the time of the last synchronization update to this
63
+ # record.
64
+ #
65
+ # Returns a Time-compatible object.
66
+ def last_synchronize
67
+ @record.synchronized_at
68
+ end
69
+
59
70
  end
60
71
 
61
72
  end
@@ -39,14 +39,6 @@ module Restforce
39
39
  Time.parse(@record.SystemModstamp)
40
40
  end
41
41
 
42
- # Public: Get the time of the last synchronization update to this
43
- # record.
44
- #
45
- # Returns a Time-compatible object.
46
- def last_synchronize
47
- last_update
48
- end
49
-
50
42
  # Public: Has this record been synced with Salesforce?
51
43
  #
52
44
  # Returns a Boolean.
@@ -18,11 +18,23 @@ module Restforce
18
18
  # Raises on any error from Salesforce.
19
19
  def create!(from_record)
20
20
  from_attributes = FieldProcessor.new.process(@record_type, from_record.attributes, :create)
21
- record_id = DB.client.create!(@record_type, from_attributes)
22
-
23
- from_record.update!(@mapping.lookup_column => record_id).after_sync
24
-
25
- find(record_id)
21
+ record_id = DB.client.upsert!(
22
+ @record_type,
23
+ "SynchronizationId__c",
24
+ from_attributes.merge("SynchronizationId__c" => from_record.uuid),
25
+ )
26
+
27
+ # NOTE: #upsert! returns a String Salesforce ID when a record is
28
+ # created, or returns `true` when an existing record was found and
29
+ # updated.
30
+ if record_id.is_a?(String)
31
+ from_record.update!(@mapping.lookup_column => record_id).after_sync
32
+ find(record_id)
33
+ else
34
+ instance = first("SynchronizationId__c = '#{from_record.uuid}'")
35
+ from_record.update!(@mapping.lookup_column => instance.id).after_sync
36
+ instance
37
+ end
26
38
  end
27
39
 
28
40
  # Public: Find the first Salesforce record which meets the passed
@@ -3,7 +3,7 @@ module Restforce
3
3
  # :nodoc:
4
4
  module DB
5
5
 
6
- VERSION = "2.7.0"
6
+ VERSION = "3.0.0"
7
7
 
8
8
  end
9
9
 
@@ -21,10 +21,10 @@ http_interactions:
21
21
  message: OK
22
22
  headers:
23
23
  Date:
24
- - Mon, 08 Jun 2015 22:13:21 GMT
24
+ - Wed, 24 Jun 2015 18:34:52 GMT
25
25
  Set-Cookie:
26
- - BrowserId=X_lZ2UPDSpeo9gWm8kD1mw;Path=/;Domain=.salesforce.com;Expires=Fri,
27
- 07-Aug-2015 22:13:21 GMT
26
+ - BrowserId=aKS8yAn1RXaQ5xLLDWvcqw;Path=/;Domain=.salesforce.com;Expires=Sun,
27
+ 23-Aug-2015 18:34:52 GMT
28
28
  Expires:
29
29
  - Thu, 01 Jan 1970 00:00:00 GMT
30
30
  Pragma:
@@ -37,9 +37,9 @@ http_interactions:
37
37
  - chunked
38
38
  body:
39
39
  encoding: ASCII-8BIT
40
- string: '{"id":"https://login.salesforce.com/id/00D1a000000H3O9EAK/0051a000000UGT8AAO","issued_at":"1433801601678","token_type":"Bearer","instance_url":"https://<host>","signature":"pCaP3SbgusCMAnEdVlM3F9fkaMe5LmtrNhBEOqAle+A=","access_token":"00D1a000000H3O9!AQ4AQH0rZGqBVji7vO4sB8J1_YW.g5S2vIbe9IaUgwHpwLPEdpfIcj9Ngpc2CndFvJZMwVIIp15.yQQOil19Qc2MuedbnlQz"}'
40
+ string: '{"id":"https://login.salesforce.com/id/00D1a000000H3O9EAK/0051a000000UGT8AAO","issued_at":"1435170892365","token_type":"Bearer","instance_url":"https://<host>","signature":"A0a5DAaWIK8kteDcmiwQXntRWHIfAq0gIi9OO00wcyk=","access_token":"00D1a000000H3O9!AQ4AQNK96zuBaEk9NKWUAyWWpuQMJkhWoqad9KZ4VwaiC5uJ8k6jTm.ILyUyydEv.pXY3IFrmILmW.cLInyzW6.ZDXbrtThl"}'
41
41
  http_version:
42
- recorded_at: Mon, 08 Jun 2015 22:13:23 GMT
42
+ recorded_at: Wed, 24 Jun 2015 18:35:00 GMT
43
43
  - request:
44
44
  method: get
45
45
  uri: https://<host>/services/data/<api_version>/query?q=select%20Id,%20SystemModstamp,%20LastModifiedById,%20Name,%20Example_Field__c%20from%20CustomObject__c
@@ -50,7 +50,7 @@ http_interactions:
50
50
  User-Agent:
51
51
  - Faraday v0.9.1
52
52
  Authorization:
53
- - OAuth 00D1a000000H3O9!AQ4AQH0rZGqBVji7vO4sB8J1_YW.g5S2vIbe9IaUgwHpwLPEdpfIcj9Ngpc2CndFvJZMwVIIp15.yQQOil19Qc2MuedbnlQz
53
+ - OAuth 00D1a000000H3O9!AQ4AQNK96zuBaEk9NKWUAyWWpuQMJkhWoqad9KZ4VwaiC5uJ8k6jTm.ILyUyydEv.pXY3IFrmILmW.cLInyzW6.ZDXbrtThl
54
54
  Accept-Encoding:
55
55
  - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
56
56
  Accept:
@@ -61,23 +61,23 @@ http_interactions:
61
61
  message: OK
62
62
  headers:
63
63
  Date:
64
- - Mon, 08 Jun 2015 22:13:21 GMT
64
+ - Wed, 24 Jun 2015 18:34:52 GMT
65
65
  Set-Cookie:
66
- - BrowserId=19TFakWMQFWE4Hk7h4zMmQ;Path=/;Domain=.salesforce.com;Expires=Fri,
67
- 07-Aug-2015 22:13:21 GMT
66
+ - BrowserId=_TMdYkP7SsKPbLFyVbQW7Q;Path=/;Domain=.salesforce.com;Expires=Sun,
67
+ 23-Aug-2015 18:34:52 GMT
68
68
  Expires:
69
69
  - Thu, 01 Jan 1970 00:00:00 GMT
70
70
  Sforce-Limit-Info:
71
- - api-usage=109/15000
71
+ - api-usage=34/15000
72
72
  Content-Type:
73
73
  - application/json;charset=UTF-8
74
74
  Transfer-Encoding:
75
75
  - chunked
76
76
  body:
77
77
  encoding: ASCII-8BIT
78
- string: '{"totalSize":1,"done":true,"records":[{"attributes":{"type":"CustomObject__c","url":"/services/data/<api_version>/sobjects/CustomObject__c/a001a000001a60JAAQ"},"Id":"a001a000001a60JAAQ","SystemModstamp":"2015-05-18T22:46:05.000+0000","LastModifiedById":"0051a000000UGT8AAO","Name":"SAMPLE","Example_Field__c":null}]}'
78
+ string: '{"totalSize":1,"done":true,"records":[{"attributes":{"type":"CustomObject__c","url":"/services/data/<api_version>/sobjects/CustomObject__c/a001a000002ze8cAAA"},"Id":"a001a000002ze8cAAA","SystemModstamp":"2015-06-24T17:05:30.000+0000","LastModifiedById":"0051a000000UGT8AAO","Name":"Testing2","Example_Field__c":null}]}'
79
79
  http_version:
80
- recorded_at: Mon, 08 Jun 2015 22:13:23 GMT
80
+ recorded_at: Wed, 24 Jun 2015 18:35:00 GMT
81
81
  - request:
82
82
  method: get
83
83
  uri: https://<host>/services/data/<api_version>/sobjects/CustomObject__c/describe
@@ -88,7 +88,7 @@ http_interactions:
88
88
  User-Agent:
89
89
  - Faraday v0.9.1
90
90
  Authorization:
91
- - OAuth 00D1a000000H3O9!AQ4AQH0rZGqBVji7vO4sB8J1_YW.g5S2vIbe9IaUgwHpwLPEdpfIcj9Ngpc2CndFvJZMwVIIp15.yQQOil19Qc2MuedbnlQz
91
+ - OAuth 00D1a000000H3O9!AQ4AQNK96zuBaEk9NKWUAyWWpuQMJkhWoqad9KZ4VwaiC5uJ8k6jTm.ILyUyydEv.pXY3IFrmILmW.cLInyzW6.ZDXbrtThl
92
92
  Accept-Encoding:
93
93
  - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
94
94
  Accept:
@@ -99,22 +99,22 @@ http_interactions:
99
99
  message: OK
100
100
  headers:
101
101
  Date:
102
- - Mon, 08 Jun 2015 22:13:22 GMT
102
+ - Wed, 24 Jun 2015 18:34:52 GMT
103
103
  Set-Cookie:
104
- - BrowserId=rh_fzB9BQPWtnSKyheqDEA;Path=/;Domain=.salesforce.com;Expires=Fri,
105
- 07-Aug-2015 22:13:22 GMT
104
+ - BrowserId=LW_-C13XRouLPEZWiq2dCw;Path=/;Domain=.salesforce.com;Expires=Sun,
105
+ 23-Aug-2015 18:34:52 GMT
106
106
  Expires:
107
107
  - Thu, 01 Jan 1970 00:00:00 GMT
108
108
  Sforce-Limit-Info:
109
- - api-usage=102/15000
109
+ - api-usage=34/15000
110
110
  Org.eclipse.jetty.server.include.etag:
111
- - 7057c783
111
+ - aa7ee96f
112
112
  Last-Modified:
113
- - Wed, 01 Apr 2015 17:47:03 GMT
113
+ - Wed, 24 Jun 2015 02:10:32 GMT
114
114
  Content-Type:
115
115
  - application/json;charset=UTF-8
116
116
  Etag:
117
- - 7057c78-gzip"
117
+ - aa7ee96-gzip"
118
118
  Transfer-Encoding:
119
119
  - chunked
120
120
  body:
@@ -128,12 +128,12 @@ http_interactions:
128
128
  Modified Date","length":0,"name":"LastModifiedDate","nameField":false,"namePointing":false,"nillable":false,"permissionable":false,"picklistValues":[],"precision":0,"referenceTo":[],"relationshipName":null,"relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"xsd:dateTime","sortable":true,"type":"datetime","unique":false,"updateable":false,"writeRequiresMasterRead":false},{"autoNumber":false,"byteLength":18,"calculated":false,"calculatedFormula":null,"cascadeDelete":false,"caseSensitive":false,"controllerName":null,"createable":false,"custom":false,"defaultValue":null,"defaultValueFormula":null,"defaultedOnCreate":true,"dependentPicklist":false,"deprecatedAndHidden":false,"digits":0,"displayLocationInDecimal":false,"externalId":false,"filterable":true,"groupable":true,"htmlFormatted":false,"idLookup":false,"inlineHelpText":null,"label":"Last
129
129
  Modified By ID","length":18,"name":"LastModifiedById","nameField":false,"namePointing":false,"nillable":false,"permissionable":false,"picklistValues":[],"precision":0,"referenceTo":["User"],"relationshipName":"LastModifiedBy","relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"tns:ID","sortable":true,"type":"reference","unique":false,"updateable":false,"writeRequiresMasterRead":false},{"autoNumber":false,"byteLength":0,"calculated":false,"calculatedFormula":null,"cascadeDelete":false,"caseSensitive":false,"controllerName":null,"createable":false,"custom":false,"defaultValue":null,"defaultValueFormula":null,"defaultedOnCreate":true,"dependentPicklist":false,"deprecatedAndHidden":false,"digits":0,"displayLocationInDecimal":false,"externalId":false,"filterable":true,"groupable":false,"htmlFormatted":false,"idLookup":false,"inlineHelpText":null,"label":"System
130
130
  Modstamp","length":0,"name":"SystemModstamp","nameField":false,"namePointing":false,"nillable":false,"permissionable":false,"picklistValues":[],"precision":0,"referenceTo":[],"relationshipName":null,"relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"xsd:dateTime","sortable":true,"type":"datetime","unique":false,"updateable":false,"writeRequiresMasterRead":false},{"autoNumber":false,"byteLength":765,"calculated":false,"calculatedFormula":null,"cascadeDelete":false,"caseSensitive":false,"controllerName":null,"createable":true,"custom":true,"defaultValue":null,"defaultValueFormula":null,"defaultedOnCreate":false,"dependentPicklist":false,"deprecatedAndHidden":false,"digits":0,"displayLocationInDecimal":false,"externalId":false,"filterable":true,"groupable":true,"htmlFormatted":false,"idLookup":false,"inlineHelpText":null,"label":"Example
131
- Field","length":255,"name":"Example_Field__c","nameField":false,"namePointing":false,"nillable":true,"permissionable":true,"picklistValues":[],"precision":0,"referenceTo":[],"relationshipName":null,"relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"xsd:string","sortable":true,"type":"string","unique":false,"updateable":true,"writeRequiresMasterRead":false},{"autoNumber":false,"byteLength":18,"calculated":false,"calculatedFormula":null,"cascadeDelete":false,"caseSensitive":false,"controllerName":null,"createable":true,"custom":true,"defaultValue":null,"defaultValueFormula":null,"defaultedOnCreate":false,"dependentPicklist":false,"deprecatedAndHidden":false,"digits":0,"displayLocationInDecimal":false,"externalId":false,"filterable":true,"groupable":true,"htmlFormatted":false,"idLookup":false,"inlineHelpText":null,"label":"Friend","length":18,"name":"Friend__c","nameField":false,"namePointing":false,"nillable":true,"permissionable":true,"picklistValues":[],"precision":0,"referenceTo":["Contact"],"relationshipName":"Friend__r","relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"tns:ID","sortable":true,"type":"reference","unique":false,"updateable":true,"writeRequiresMasterRead":false},{"autoNumber":false,"byteLength":0,"calculated":false,"calculatedFormula":null,"cascadeDelete":false,"caseSensitive":false,"controllerName":null,"createable":true,"custom":true,"defaultValue":null,"defaultValueFormula":null,"defaultedOnCreate":true,"dependentPicklist":false,"deprecatedAndHidden":false,"digits":0,"displayLocationInDecimal":false,"externalId":false,"filterable":true,"groupable":true,"htmlFormatted":false,"idLookup":false,"inlineHelpText":null,"label":"Visible","length":0,"name":"Visible__c","nameField":false,"namePointing":false,"nillable":false,"permissionable":true,"picklistValues":[],"precision":0,"referenceTo":[],"relationshipName":null,"relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"xsd:boolean","sortable":true,"type":"boolean","unique":false,"updateable":true,"writeRequiresMasterRead":false}],"keyPrefix":"a00","label":"CustomObject","labelPlural":"CustomObjects","layoutable":true,"listviewable":null,"lookupLayoutable":null,"mergeable":false,"name":"CustomObject__c","queryable":true,"recordTypeInfos":[{"available":true,"defaultRecordTypeMapping":true,"name":"Master","recordTypeId":"012000000000000AAA","urls":{"layout":"/services/data/<api_version>/sobjects/CustomObject__c/describe/layouts/012000000000000AAA"}}],"replicateable":true,"retrieveable":true,"searchLayoutable":true,"searchable":true,"triggerable":true,"undeletable":true,"updateable":true,"urls":{"uiEditTemplate":"https://<host>/{ID}/e","sobject":"/services/data/<api_version>/sobjects/CustomObject__c","quickActions":"/services/data/<api_version>/sobjects/CustomObject__c/quickActions","uiDetailTemplate":"https://<host>/{ID}","describe":"/services/data/<api_version>/sobjects/CustomObject__c/describe","rowTemplate":"/services/data/<api_version>/sobjects/CustomObject__c/{ID}","layouts":"/services/data/<api_version>/sobjects/CustomObject__c/describe/layouts","compactLayouts":"/services/data/<api_version>/sobjects/CustomObject__c/describe/compactLayouts","uiNewRecord":"https://<host>/a00/e"}}'
131
+ Field","length":255,"name":"Example_Field__c","nameField":false,"namePointing":false,"nillable":true,"permissionable":true,"picklistValues":[],"precision":0,"referenceTo":[],"relationshipName":null,"relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"xsd:string","sortable":true,"type":"string","unique":false,"updateable":true,"writeRequiresMasterRead":false},{"autoNumber":false,"byteLength":18,"calculated":false,"calculatedFormula":null,"cascadeDelete":false,"caseSensitive":false,"controllerName":null,"createable":true,"custom":true,"defaultValue":null,"defaultValueFormula":null,"defaultedOnCreate":false,"dependentPicklist":false,"deprecatedAndHidden":false,"digits":0,"displayLocationInDecimal":false,"externalId":false,"filterable":true,"groupable":true,"htmlFormatted":false,"idLookup":false,"inlineHelpText":null,"label":"Friend","length":18,"name":"Friend__c","nameField":false,"namePointing":false,"nillable":true,"permissionable":true,"picklistValues":[],"precision":0,"referenceTo":["Contact"],"relationshipName":"Friend__r","relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"tns:ID","sortable":true,"type":"reference","unique":false,"updateable":true,"writeRequiresMasterRead":false},{"autoNumber":false,"byteLength":0,"calculated":false,"calculatedFormula":null,"cascadeDelete":false,"caseSensitive":false,"controllerName":null,"createable":true,"custom":true,"defaultValue":null,"defaultValueFormula":null,"defaultedOnCreate":true,"dependentPicklist":false,"deprecatedAndHidden":false,"digits":0,"displayLocationInDecimal":false,"externalId":false,"filterable":true,"groupable":true,"htmlFormatted":false,"idLookup":false,"inlineHelpText":null,"label":"Visible","length":0,"name":"Visible__c","nameField":false,"namePointing":false,"nillable":false,"permissionable":true,"picklistValues":[],"precision":0,"referenceTo":[],"relationshipName":null,"relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"xsd:boolean","sortable":true,"type":"boolean","unique":false,"updateable":true,"writeRequiresMasterRead":false},{"autoNumber":false,"byteLength":108,"calculated":false,"calculatedFormula":null,"cascadeDelete":false,"caseSensitive":false,"controllerName":null,"createable":true,"custom":true,"defaultValue":null,"defaultValueFormula":null,"defaultedOnCreate":false,"dependentPicklist":false,"deprecatedAndHidden":false,"digits":0,"displayLocationInDecimal":false,"externalId":true,"filterable":true,"groupable":true,"htmlFormatted":false,"idLookup":true,"inlineHelpText":null,"label":"SynchronizationID","length":36,"name":"SynchronizationId__c","nameField":false,"namePointing":false,"nillable":true,"permissionable":true,"picklistValues":[],"precision":0,"referenceTo":[],"relationshipName":null,"relationshipOrder":null,"restrictedDelete":false,"restrictedPicklist":false,"scale":0,"soapType":"xsd:string","sortable":true,"type":"string","unique":false,"updateable":true,"writeRequiresMasterRead":false}],"keyPrefix":"a00","label":"CustomObject","labelPlural":"CustomObjects","layoutable":true,"listviewable":null,"lookupLayoutable":null,"mergeable":false,"name":"CustomObject__c","queryable":true,"recordTypeInfos":[{"available":true,"defaultRecordTypeMapping":true,"name":"Master","recordTypeId":"012000000000000AAA","urls":{"layout":"/services/data/<api_version>/sobjects/CustomObject__c/describe/layouts/012000000000000AAA"}}],"replicateable":true,"retrieveable":true,"searchLayoutable":true,"searchable":true,"triggerable":true,"undeletable":true,"updateable":true,"urls":{"uiEditTemplate":"https://<host>/{ID}/e","sobject":"/services/data/<api_version>/sobjects/CustomObject__c","quickActions":"/services/data/<api_version>/sobjects/CustomObject__c/quickActions","uiDetailTemplate":"https://<host>/{ID}","describe":"/services/data/<api_version>/sobjects/CustomObject__c/describe","rowTemplate":"/services/data/<api_version>/sobjects/CustomObject__c/{ID}","layouts":"/services/data/<api_version>/sobjects/CustomObject__c/describe/layouts","compactLayouts":"/services/data/<api_version>/sobjects/CustomObject__c/describe/compactLayouts","uiNewRecord":"https://<host>/a00/e"}}'
132
132
  http_version:
133
- recorded_at: Mon, 08 Jun 2015 22:13:23 GMT
133
+ recorded_at: Wed, 24 Jun 2015 18:35:00 GMT
134
134
  - request:
135
- method: post
136
- uri: https://<host>/services/data/<api_version>/sobjects/CustomObject__c
135
+ method: patch
136
+ uri: https://<host>/services/data/<api_version>/sobjects/CustomObject__c/SynchronizationId__c/CustomObject::1
137
137
  body:
138
138
  encoding: UTF-8
139
139
  string: '{"Name":"Custom object","Example_Field__c":"Some sample text"}'
@@ -143,7 +143,7 @@ http_interactions:
143
143
  Content-Type:
144
144
  - application/json
145
145
  Authorization:
146
- - OAuth 00D1a000000H3O9!AQ4AQH0rZGqBVji7vO4sB8J1_YW.g5S2vIbe9IaUgwHpwLPEdpfIcj9Ngpc2CndFvJZMwVIIp15.yQQOil19Qc2MuedbnlQz
146
+ - OAuth 00D1a000000H3O9!AQ4AQNK96zuBaEk9NKWUAyWWpuQMJkhWoqad9KZ4VwaiC5uJ8k6jTm.ILyUyydEv.pXY3IFrmILmW.cLInyzW6.ZDXbrtThl
147
147
  Accept-Encoding:
148
148
  - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
149
149
  Accept:
@@ -154,28 +154,28 @@ http_interactions:
154
154
  message: Created
155
155
  headers:
156
156
  Date:
157
- - Mon, 08 Jun 2015 22:13:22 GMT
157
+ - Wed, 24 Jun 2015 18:34:53 GMT
158
158
  Set-Cookie:
159
- - BrowserId=Gj7Hz1IoQRSGl1N5Ac2SMw;Path=/;Domain=.salesforce.com;Expires=Fri,
160
- 07-Aug-2015 22:13:22 GMT
159
+ - BrowserId=mmlGpTRaTUa8h8XOKyh2eQ;Path=/;Domain=.salesforce.com;Expires=Sun,
160
+ 23-Aug-2015 18:34:53 GMT
161
161
  Expires:
162
162
  - Thu, 01 Jan 1970 00:00:00 GMT
163
163
  Sforce-Limit-Info:
164
- - api-usage=98/15000
164
+ - api-usage=34/15000
165
165
  Location:
166
- - "/services/data/<api_version>/sobjects/CustomObject__c/a001a000001cF7fAAE"
166
+ - "/services/data/<api_version>/sobjects/CustomObject__c/a001a000002zeDhAAI"
167
167
  Content-Type:
168
168
  - application/json;charset=UTF-8
169
169
  Transfer-Encoding:
170
170
  - chunked
171
171
  body:
172
- encoding: ASCII-8BIT
173
- string: '{"id":"a001a000001cF7fAAE","success":true,"errors":[]}'
172
+ encoding: UTF-8
173
+ string: '{"id":"a001a000002zeDhAAI","success":true,"errors":[]}'
174
174
  http_version:
175
- recorded_at: Mon, 08 Jun 2015 22:13:23 GMT
175
+ recorded_at: Wed, 24 Jun 2015 18:35:01 GMT
176
176
  - request:
177
177
  method: get
178
- uri: https://<host>/services/data/<api_version>/query?q=select%20Id,%20SystemModstamp,%20LastModifiedById,%20Name,%20Example_Field__c%20from%20CustomObject__c%20where%20Id%20=%20%27a001a000001cF7fAAE%27
178
+ uri: https://<host>/services/data/<api_version>/query?q=select%20Id,%20SystemModstamp,%20LastModifiedById,%20Name,%20Example_Field__c%20from%20CustomObject__c%20where%20Id%20=%20%27a001a000002zeDhAAI%27
179
179
  body:
180
180
  encoding: US-ASCII
181
181
  string: ''
@@ -183,7 +183,7 @@ http_interactions:
183
183
  User-Agent:
184
184
  - Faraday v0.9.1
185
185
  Authorization:
186
- - OAuth 00D1a000000H3O9!AQ4AQH0rZGqBVji7vO4sB8J1_YW.g5S2vIbe9IaUgwHpwLPEdpfIcj9Ngpc2CndFvJZMwVIIp15.yQQOil19Qc2MuedbnlQz
186
+ - OAuth 00D1a000000H3O9!AQ4AQNK96zuBaEk9NKWUAyWWpuQMJkhWoqad9KZ4VwaiC5uJ8k6jTm.ILyUyydEv.pXY3IFrmILmW.cLInyzW6.ZDXbrtThl
187
187
  Accept-Encoding:
188
188
  - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
189
189
  Accept:
@@ -194,27 +194,27 @@ http_interactions:
194
194
  message: OK
195
195
  headers:
196
196
  Date:
197
- - Mon, 08 Jun 2015 22:13:22 GMT
197
+ - Wed, 24 Jun 2015 18:34:53 GMT
198
198
  Set-Cookie:
199
- - BrowserId=WYNqGU1RREa7eAYGEJMtzw;Path=/;Domain=.salesforce.com;Expires=Fri,
200
- 07-Aug-2015 22:13:22 GMT
199
+ - BrowserId=FMKsCORzSPGqpi2wDE2yFw;Path=/;Domain=.salesforce.com;Expires=Sun,
200
+ 23-Aug-2015 18:34:53 GMT
201
201
  Expires:
202
202
  - Thu, 01 Jan 1970 00:00:00 GMT
203
203
  Sforce-Limit-Info:
204
- - api-usage=99/15000
204
+ - api-usage=34/15000
205
205
  Content-Type:
206
206
  - application/json;charset=UTF-8
207
207
  Transfer-Encoding:
208
208
  - chunked
209
209
  body:
210
210
  encoding: ASCII-8BIT
211
- string: '{"totalSize":1,"done":true,"records":[{"attributes":{"type":"CustomObject__c","url":"/services/data/<api_version>/sobjects/CustomObject__c/a001a000001cF7fAAE"},"Id":"a001a000001cF7fAAE","SystemModstamp":"2015-06-08T22:13:22.000+0000","LastModifiedById":"0051a000000UGT8AAO","Name":"Custom
211
+ string: '{"totalSize":1,"done":true,"records":[{"attributes":{"type":"CustomObject__c","url":"/services/data/<api_version>/sobjects/CustomObject__c/a001a000002zeDhAAI"},"Id":"a001a000002zeDhAAI","SystemModstamp":"2015-06-24T18:34:53.000+0000","LastModifiedById":"0051a000000UGT8AAO","Name":"Custom
212
212
  object","Example_Field__c":"Some sample text"}]}'
213
213
  http_version:
214
- recorded_at: Mon, 08 Jun 2015 22:13:24 GMT
214
+ recorded_at: Wed, 24 Jun 2015 18:35:01 GMT
215
215
  - request:
216
216
  method: get
217
- uri: https://<host>/services/data/<api_version>/query?q=select%20Id,%20SystemModstamp,%20LastModifiedById,%20Name,%20Example_Field__c%20from%20CustomObject__c%20where%20Id%20=%20%27a001a000001cF7fAAE%27
217
+ uri: https://<host>/services/data/<api_version>/query?q=select%20Id,%20SystemModstamp,%20LastModifiedById,%20Name,%20Example_Field__c%20from%20CustomObject__c%20where%20Id%20=%20%27a001a000002zeDhAAI%27
218
218
  body:
219
219
  encoding: US-ASCII
220
220
  string: ''
@@ -222,7 +222,7 @@ http_interactions:
222
222
  User-Agent:
223
223
  - Faraday v0.9.1
224
224
  Authorization:
225
- - OAuth 00D1a000000H3O9!AQ4AQH0rZGqBVji7vO4sB8J1_YW.g5S2vIbe9IaUgwHpwLPEdpfIcj9Ngpc2CndFvJZMwVIIp15.yQQOil19Qc2MuedbnlQz
225
+ - OAuth 00D1a000000H3O9!AQ4AQNK96zuBaEk9NKWUAyWWpuQMJkhWoqad9KZ4VwaiC5uJ8k6jTm.ILyUyydEv.pXY3IFrmILmW.cLInyzW6.ZDXbrtThl
226
226
  Accept-Encoding:
227
227
  - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
228
228
  Accept:
@@ -233,27 +233,27 @@ http_interactions:
233
233
  message: OK
234
234
  headers:
235
235
  Date:
236
- - Mon, 08 Jun 2015 22:13:22 GMT
236
+ - Wed, 24 Jun 2015 18:34:53 GMT
237
237
  Set-Cookie:
238
- - BrowserId=sj5L_u3dTXWmAVEUVMSCKA;Path=/;Domain=.salesforce.com;Expires=Fri,
239
- 07-Aug-2015 22:13:22 GMT
238
+ - BrowserId=KxgLmlPAQji8dJHgvKiYfQ;Path=/;Domain=.salesforce.com;Expires=Sun,
239
+ 23-Aug-2015 18:34:53 GMT
240
240
  Expires:
241
241
  - Thu, 01 Jan 1970 00:00:00 GMT
242
242
  Sforce-Limit-Info:
243
- - api-usage=106/15000
243
+ - api-usage=35/15000
244
244
  Content-Type:
245
245
  - application/json;charset=UTF-8
246
246
  Transfer-Encoding:
247
247
  - chunked
248
248
  body:
249
249
  encoding: ASCII-8BIT
250
- string: '{"totalSize":1,"done":true,"records":[{"attributes":{"type":"CustomObject__c","url":"/services/data/<api_version>/sobjects/CustomObject__c/a001a000001cF7fAAE"},"Id":"a001a000001cF7fAAE","SystemModstamp":"2015-06-08T22:13:22.000+0000","LastModifiedById":"0051a000000UGT8AAO","Name":"Custom
250
+ string: '{"totalSize":1,"done":true,"records":[{"attributes":{"type":"CustomObject__c","url":"/services/data/<api_version>/sobjects/CustomObject__c/a001a000002zeDhAAI"},"Id":"a001a000002zeDhAAI","SystemModstamp":"2015-06-24T18:34:53.000+0000","LastModifiedById":"0051a000000UGT8AAO","Name":"Custom
251
251
  object","Example_Field__c":"Some sample text"}]}'
252
252
  http_version:
253
- recorded_at: Mon, 08 Jun 2015 22:13:24 GMT
253
+ recorded_at: Wed, 24 Jun 2015 18:35:01 GMT
254
254
  - request:
255
255
  method: delete
256
- uri: https://<host>/services/data/<api_version>/sobjects/CustomObject__c/a001a000001cF7fAAE
256
+ uri: https://<host>/services/data/<api_version>/sobjects/CustomObject__c/a001a000002zeDhAAI
257
257
  body:
258
258
  encoding: US-ASCII
259
259
  string: ''
@@ -261,7 +261,7 @@ http_interactions:
261
261
  User-Agent:
262
262
  - Faraday v0.9.1
263
263
  Authorization:
264
- - OAuth 00D1a000000H3O9!AQ4AQH0rZGqBVji7vO4sB8J1_YW.g5S2vIbe9IaUgwHpwLPEdpfIcj9Ngpc2CndFvJZMwVIIp15.yQQOil19Qc2MuedbnlQz
264
+ - OAuth 00D1a000000H3O9!AQ4AQNK96zuBaEk9NKWUAyWWpuQMJkhWoqad9KZ4VwaiC5uJ8k6jTm.ILyUyydEv.pXY3IFrmILmW.cLInyzW6.ZDXbrtThl
265
265
  Accept-Encoding:
266
266
  - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
267
267
  Accept:
@@ -272,17 +272,17 @@ http_interactions:
272
272
  message: No Content
273
273
  headers:
274
274
  Date:
275
- - Mon, 08 Jun 2015 22:13:22 GMT
275
+ - Wed, 24 Jun 2015 18:34:53 GMT
276
276
  Set-Cookie:
277
- - BrowserId=jMXklkWqRY2qJXIZ9hwyfw;Path=/;Domain=.salesforce.com;Expires=Fri,
278
- 07-Aug-2015 22:13:22 GMT
277
+ - BrowserId=QANHelrFTM-AFubF5KfZpw;Path=/;Domain=.salesforce.com;Expires=Sun,
278
+ 23-Aug-2015 18:34:53 GMT
279
279
  Expires:
280
280
  - Thu, 01 Jan 1970 00:00:00 GMT
281
281
  Sforce-Limit-Info:
282
- - api-usage=104/15000
282
+ - api-usage=34/15000
283
283
  body:
284
284
  encoding: UTF-8
285
285
  string: ''
286
286
  http_version:
287
- recorded_at: Mon, 08 Jun 2015 22:13:24 GMT
287
+ recorded_at: Wed, 24 Jun 2015 18:35:01 GMT
288
288
  recorded_with: VCR 2.9.3