restforce-db 0.3.4 → 0.3.5

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
  SHA1:
3
- metadata.gz: 5b2f8154faa82f569ece3b6f591dd527f4adb723
4
- data.tar.gz: daddd3d9d7601222b1afd816e42d45aa9b11453d
3
+ metadata.gz: 36ac23672709a2d24f9193d4d8cabbaf0bcb4e35
4
+ data.tar.gz: 8d9f0bbeab71f7a1edf1c6159887f63b27865708
5
5
  SHA512:
6
- metadata.gz: fbc8532491a16de2fb62c1ad1076a326f9eca24ae5e6bc7f18f44e157b0f4a7901887688c0afa405fe66211bf9093587ef555232f3612ca4e23907c0ec4920c6
7
- data.tar.gz: 921d7933ef5c198dd382e578b8e0176515f8587b05c29dbf8c53ad0a30c3be984c5b1b516e40e9a5a162066bb66f57c6217a24b0a71eacd3ed2b09fbdc07af3d
6
+ metadata.gz: ff1d1b1d71a0a506dbae3b3aa9990474c2e9800bef66987040d9df20b790bc2eb6720330cbf69fc71c1fd3ef2f321ae16f0607bacb1648920c5f7decd7c2a698
7
+ data.tar.gz: 0152fb60d9d3a91ff76943c7be5cf64f480c365b46cd768bfbb224b9ac2c4f965db913f51b9a850134e653440f7df2ec755c31108a32132160fa2b6690e5f311
@@ -83,6 +83,9 @@ module Restforce
83
83
  opt.on("-c FILE", "--config FILE", "The location of a Restforce credentials file.") do |file|
84
84
  @options[:config] = file
85
85
  end
86
+ opt.on("-d N", "--delay N", "Amount of time by which to delay synchronization queries.") do |n|
87
+ @options[:delay] = n.to_f
88
+ end
86
89
  opt.on("-i N", "--interval N", "Amount of time to wait between synchronizations.") do |n|
87
90
  @options[:interval] = n.to_i
88
91
  end
@@ -35,12 +35,27 @@ module Restforce
35
35
  #
36
36
  # Returns nothing.
37
37
  def load(configurations)
38
- self.username = configurations["username"]
39
- self.password = configurations["password"]
40
- self.security_token = configurations["security_token"]
41
- self.client_id = configurations["client_id"]
42
- self.client_secret = configurations["client_secret"]
43
- self.host = configurations["host"]
38
+ self.username = parsed(configurations, "username")
39
+ self.password = parsed(configurations, "password")
40
+ self.security_token = parsed(configurations, "security_token")
41
+ self.client_id = parsed(configurations, "client_id")
42
+ self.client_secret = parsed(configurations, "client_secret")
43
+ self.host = parsed(configurations, "host")
44
+ end
45
+
46
+ private
47
+
48
+ # Internal: Get the requested setting from a Hash of configurations.
49
+ #
50
+ # configurations - A Hash of configurations.
51
+ # setting - A String name of a single configuration in the Hash.
52
+ #
53
+ # Returns the value of the setting.
54
+ # Raises ArgumentError if the setting is not contained in the Hash.
55
+ def parsed(configurations, setting)
56
+ configurations.fetch setting do |key|
57
+ raise ArgumentError, "Configuration is missing #{key}"
58
+ end
44
59
  end
45
60
 
46
61
  end
@@ -36,7 +36,12 @@ module Restforce
36
36
 
37
37
  self.collection ||= {}
38
38
 
39
- attr_reader :database_record_type, :salesforce_record_type, :associations
39
+ attr_reader(
40
+ :database_record_type,
41
+ :salesforce_record_type,
42
+ :associations,
43
+ :conditions,
44
+ )
40
45
  attr_writer :root
41
46
 
42
47
  # Public: Initialize a new Restforce::DB::Mapping.
@@ -50,6 +55,9 @@ module Restforce
50
55
  # :associations - A Hash of mappings between Active
51
56
  # Record association names and the
52
57
  # corresponding Salesforce Lookup name.
58
+ # :conditions - An Array of lookup conditions which
59
+ # should be applied to the Salesforce
60
+ # queries.
53
61
  # :root - A Boolean reflecting whether or not
54
62
  # this is a root-level mapping.
55
63
  def initialize(database_model, salesforce_model, options = {})
@@ -58,6 +66,7 @@ module Restforce
58
66
 
59
67
  @fields = options.fetch(:fields) { {} }
60
68
  @associations = options.fetch(:associations) { {} }
69
+ @conditions = options.fetch(:conditions) { [] }
61
70
  @root = options.fetch(:root) { false }
62
71
 
63
72
  @types = {
@@ -8,6 +8,8 @@ module Restforce
8
8
  # models defined in the Restforce::DB::RecordTypes namespace.
9
9
  class Base
10
10
 
11
+ include Enumerable
12
+
11
13
  # Public: Initialize a new Restforce::DB::RecordTypes::Base.
12
14
  #
13
15
  # record_type - The name or class of the system record type.
@@ -31,10 +31,7 @@ module Restforce
31
31
  #
32
32
  # Returns nil or a Restforce::DB::Instances::Salesforce instance.
33
33
  def find(id)
34
- record = DB.client.query(
35
- "select #{lookups} from #{@record_type} where Id = '#{id}'",
36
- ).first
37
-
34
+ record = DB.client.query(query("Id = '#{id}'")).first
38
35
  return unless record
39
36
 
40
37
  Instances::Salesforce.new(@record_type, record, @mapping)
@@ -53,14 +50,11 @@ module Restforce
53
50
  # Returns nothing.
54
51
  def each(options = {})
55
52
  constraints = [
56
- ("SystemModstamp <= #{options[:before].utc.iso8601}" if options[:before]),
57
- ("SystemModstamp > #{options[:after].utc.iso8601}" if options[:after]),
58
- ].compact.join(" and ")
59
- constraints = " where #{constraints}" unless constraints.empty?
60
-
61
- query = "select #{lookups} from #{@record_type}#{constraints}"
53
+ ("SystemModstamp < #{options[:before].utc.iso8601}" if options[:before]),
54
+ ("SystemModstamp >= #{options[:after].utc.iso8601}" if options[:after]),
55
+ ]
62
56
 
63
- DB.client.query(query).each do |record|
57
+ DB.client.query(query(*constraints)).each do |record|
64
58
  yield Instances::Salesforce.new(@record_type, record, @mapping)
65
59
  end
66
60
  end
@@ -86,6 +80,18 @@ module Restforce
86
80
  record.synced?
87
81
  end
88
82
 
83
+ # Internal: Get a query String, given an Array of existing conditions.
84
+ #
85
+ # conditions - An Array of conditions to append to the query.
86
+ #
87
+ # Returns a String.
88
+ def query(*conditions)
89
+ filters = (conditions + @mapping.conditions).compact.join(" and ")
90
+ filters = " where #{filters}" unless filters.empty?
91
+
92
+ "select #{lookups} from #{@record_type}#{filters}"
93
+ end
94
+
89
95
  end
90
96
 
91
97
  end
@@ -34,16 +34,22 @@ module Restforce
34
34
  # overwriting recent changes to the database, in the event that Salesforce
35
35
  # has also been updated since the last sync.
36
36
  #
37
- # options - A Hash of options for configuring the run. Currently unused.
37
+ # options - A Hash of options for configuring the run. Valid keys are:
38
+ # :delay - An offset to apply to the time filters. Allows the
39
+ # synchronization to account for server time drift.
38
40
  #
39
41
  # Returns the Time the run was performed.
40
- def run(_options = {})
42
+ def run(options = {})
41
43
  run_time = Time.now
42
44
 
43
- @salesforce_record_type.each(after: last_run, before: run_time) do |record|
45
+ delay = options.fetch(:delay) { 0 }
46
+ before = run_time - delay
47
+ after = last_run - delay if last_run
48
+
49
+ @salesforce_record_type.each(after: after, before: before) do |record|
44
50
  @database_record_type.sync!(record)
45
51
  end
46
- @database_record_type.each(after: last_run, before: run_time) do |record|
52
+ @database_record_type.each(after: after, before: before) do |record|
47
53
  @salesforce_record_type.sync!(record)
48
54
  end
49
55
 
@@ -3,7 +3,7 @@ module Restforce
3
3
  # :nodoc:
4
4
  module DB
5
5
 
6
- VERSION = "0.3.4"
6
+ VERSION = "0.3.5"
7
7
 
8
8
  end
9
9
 
@@ -7,6 +7,7 @@ module Restforce
7
7
  class Worker
8
8
 
9
9
  DEFAULT_INTERVAL = 5
10
+ DEFAULT_DELAY = 1
10
11
 
11
12
  class << self
12
13
 
@@ -51,6 +52,7 @@ module Restforce
51
52
  def initialize(options = {})
52
53
  @verbose = options.fetch(:verbose) { false }
53
54
  @interval = options.fetch(:interval) { DEFAULT_INTERVAL }
55
+ @delay = options.fetch(:delay) { DEFAULT_DELAY }
54
56
 
55
57
  Restforce::DB.reset
56
58
  Restforce::DB.configure { |config| config.parse(options[:config]) }
@@ -136,7 +138,7 @@ module Restforce
136
138
  # Returns a Boolean.
137
139
  def synchronize(name, mapping)
138
140
  log " SYNCHRONIZE #{name}"
139
- runtime = Benchmark.realtime { mapping.synchronizer.run }
141
+ runtime = Benchmark.realtime { mapping.synchronizer.run(delay: @delay) }
140
142
  log format(" COMPLETE after %.4f", runtime)
141
143
 
142
144
  return true
@@ -0,0 +1,158 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: post
5
+ uri: https://<host>/services/oauth2/token
6
+ body:
7
+ encoding: US-ASCII
8
+ string: grant_type=password&client_id=<client_id>&client_secret=<client_secret>&username=<username>&password=<password><security_token>
9
+ headers:
10
+ User-Agent:
11
+ - Faraday v0.9.1
12
+ Content-Type:
13
+ - application/x-www-form-urlencoded
14
+ Accept-Encoding:
15
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
16
+ Accept:
17
+ - "*/*"
18
+ response:
19
+ status:
20
+ code: 200
21
+ message: OK
22
+ headers:
23
+ Date:
24
+ - Wed, 01 Apr 2015 17:42:48 GMT
25
+ Set-Cookie:
26
+ - BrowserId=8KpISBKERgy2g417EyCKJg;Path=/;Domain=.salesforce.com;Expires=Sun,
27
+ 31-May-2015 17:42:48 GMT
28
+ Expires:
29
+ - Thu, 01 Jan 1970 00:00:00 GMT
30
+ Pragma:
31
+ - no-cache
32
+ Cache-Control:
33
+ - no-cache, no-store
34
+ Content-Type:
35
+ - application/json;charset=UTF-8
36
+ Transfer-Encoding:
37
+ - chunked
38
+ body:
39
+ encoding: ASCII-8BIT
40
+ string: '{"id":"https://login.salesforce.com/id/00D1a000000H3O9EAK/0051a000000UGT8AAO","issued_at":"1427910168476","token_type":"Bearer","instance_url":"https://<host>","signature":"NrGCnWPtuW3F1C8VyTV7HxO5FJosOMjVa/Mp89FnAAE=","access_token":"00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW"}'
41
+ http_version:
42
+ recorded_at: Wed, 01 Apr 2015 17:42:48 GMT
43
+ - request:
44
+ method: post
45
+ uri: https://<host>/services/data/v26.0/sobjects/CustomObject__c
46
+ body:
47
+ encoding: UTF-8
48
+ string: '{"Name":"Sample object"}'
49
+ headers:
50
+ User-Agent:
51
+ - Faraday v0.9.1
52
+ Content-Type:
53
+ - application/json
54
+ Authorization:
55
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
56
+ Accept-Encoding:
57
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
58
+ Accept:
59
+ - "*/*"
60
+ response:
61
+ status:
62
+ code: 201
63
+ message: Created
64
+ headers:
65
+ Date:
66
+ - Wed, 01 Apr 2015 17:42:49 GMT
67
+ Set-Cookie:
68
+ - BrowserId=ZOjtoPSFTMiVnF96dDQ83w;Path=/;Domain=.salesforce.com;Expires=Sun,
69
+ 31-May-2015 17:42:49 GMT
70
+ Expires:
71
+ - Thu, 01 Jan 1970 00:00:00 GMT
72
+ Sforce-Limit-Info:
73
+ - api-usage=11/15000
74
+ Location:
75
+ - "/services/data/v26.0/sobjects/CustomObject__c/a001a000001LFfsAAG"
76
+ Content-Type:
77
+ - application/json;charset=UTF-8
78
+ Transfer-Encoding:
79
+ - chunked
80
+ body:
81
+ encoding: ASCII-8BIT
82
+ string: '{"id":"a001a000001LFfsAAG","success":true,"errors":[]}'
83
+ http_version:
84
+ recorded_at: Wed, 01 Apr 2015 17:42:49 GMT
85
+ - request:
86
+ method: get
87
+ uri: https://<host>/services/data/v26.0/query?q=select%20Id,%20SystemModstamp,%20Name,%20Example_Field__c%20from%20CustomObject__c
88
+ body:
89
+ encoding: US-ASCII
90
+ string: ''
91
+ headers:
92
+ User-Agent:
93
+ - Faraday v0.9.1
94
+ Authorization:
95
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
96
+ Accept-Encoding:
97
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
98
+ Accept:
99
+ - "*/*"
100
+ response:
101
+ status:
102
+ code: 200
103
+ message: OK
104
+ headers:
105
+ Date:
106
+ - Wed, 01 Apr 2015 17:42:50 GMT
107
+ Set-Cookie:
108
+ - BrowserId=9SFfcrRjRlqc6KnrgdGKyg;Path=/;Domain=.salesforce.com;Expires=Sun,
109
+ 31-May-2015 17:42:50 GMT
110
+ Expires:
111
+ - Thu, 01 Jan 1970 00:00:00 GMT
112
+ Sforce-Limit-Info:
113
+ - api-usage=11/15000
114
+ Content-Type:
115
+ - application/json;charset=UTF-8
116
+ Transfer-Encoding:
117
+ - chunked
118
+ body:
119
+ encoding: ASCII-8BIT
120
+ string: '{"totalSize":1,"done":true,"records":[{"attributes":{"type":"CustomObject__c","url":"/services/data/v26.0/sobjects/CustomObject__c/a001a000001LFfsAAG"},"Id":"a001a000001LFfsAAG","SystemModstamp":"2015-04-01T17:42:49.000+0000","Name":"Sample
121
+ object","Example_Field__c":null}]}'
122
+ http_version:
123
+ recorded_at: Wed, 01 Apr 2015 17:42:50 GMT
124
+ - request:
125
+ method: delete
126
+ uri: https://<host>/services/data/v26.0/sobjects/CustomObject__c/a001a000001LFfsAAG
127
+ body:
128
+ encoding: US-ASCII
129
+ string: ''
130
+ headers:
131
+ User-Agent:
132
+ - Faraday v0.9.1
133
+ Authorization:
134
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
135
+ Accept-Encoding:
136
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
137
+ Accept:
138
+ - "*/*"
139
+ response:
140
+ status:
141
+ code: 204
142
+ message: No Content
143
+ headers:
144
+ Date:
145
+ - Wed, 01 Apr 2015 17:42:51 GMT
146
+ Set-Cookie:
147
+ - BrowserId=aX4v74VsTo2dEyXmodEWrw;Path=/;Domain=.salesforce.com;Expires=Sun,
148
+ 31-May-2015 17:42:51 GMT
149
+ Expires:
150
+ - Thu, 01 Jan 1970 00:00:00 GMT
151
+ Sforce-Limit-Info:
152
+ - api-usage=11/15000
153
+ body:
154
+ encoding: UTF-8
155
+ string: ''
156
+ http_version:
157
+ recorded_at: Wed, 01 Apr 2015 17:42:52 GMT
158
+ recorded_with: VCR 2.9.3
@@ -0,0 +1,157 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: post
5
+ uri: https://<host>/services/oauth2/token
6
+ body:
7
+ encoding: US-ASCII
8
+ string: grant_type=password&client_id=<client_id>&client_secret=<client_secret>&username=<username>&password=<password><security_token>
9
+ headers:
10
+ User-Agent:
11
+ - Faraday v0.9.1
12
+ Content-Type:
13
+ - application/x-www-form-urlencoded
14
+ Accept-Encoding:
15
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
16
+ Accept:
17
+ - "*/*"
18
+ response:
19
+ status:
20
+ code: 200
21
+ message: OK
22
+ headers:
23
+ Date:
24
+ - Wed, 01 Apr 2015 17:51:22 GMT
25
+ Set-Cookie:
26
+ - BrowserId=y9Xwyc7sRiS-SYlyinh-gg;Path=/;Domain=.salesforce.com;Expires=Sun,
27
+ 31-May-2015 17:51:22 GMT
28
+ Expires:
29
+ - Thu, 01 Jan 1970 00:00:00 GMT
30
+ Pragma:
31
+ - no-cache
32
+ Cache-Control:
33
+ - no-cache, no-store
34
+ Content-Type:
35
+ - application/json;charset=UTF-8
36
+ Transfer-Encoding:
37
+ - chunked
38
+ body:
39
+ encoding: ASCII-8BIT
40
+ string: '{"id":"https://login.salesforce.com/id/00D1a000000H3O9EAK/0051a000000UGT8AAO","issued_at":"1427910682943","token_type":"Bearer","instance_url":"https://<host>","signature":"XV2VCZfDmhSb6On2Br5cxsAz/NvNH3JlkOdbLX/clPY=","access_token":"00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW"}'
41
+ http_version:
42
+ recorded_at: Wed, 01 Apr 2015 17:51:23 GMT
43
+ - request:
44
+ method: post
45
+ uri: https://<host>/services/data/v26.0/sobjects/CustomObject__c
46
+ body:
47
+ encoding: UTF-8
48
+ string: '{"Visible__c":false}'
49
+ headers:
50
+ User-Agent:
51
+ - Faraday v0.9.1
52
+ Content-Type:
53
+ - application/json
54
+ Authorization:
55
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
56
+ Accept-Encoding:
57
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
58
+ Accept:
59
+ - "*/*"
60
+ response:
61
+ status:
62
+ code: 201
63
+ message: Created
64
+ headers:
65
+ Date:
66
+ - Wed, 01 Apr 2015 17:51:23 GMT
67
+ Set-Cookie:
68
+ - BrowserId=Kfkv4LuQR3-iN46hIDKtug;Path=/;Domain=.salesforce.com;Expires=Sun,
69
+ 31-May-2015 17:51:23 GMT
70
+ Expires:
71
+ - Thu, 01 Jan 1970 00:00:00 GMT
72
+ Sforce-Limit-Info:
73
+ - api-usage=17/15000
74
+ Location:
75
+ - "/services/data/v26.0/sobjects/CustomObject__c/a001a000001LFgMAAW"
76
+ Content-Type:
77
+ - application/json;charset=UTF-8
78
+ Transfer-Encoding:
79
+ - chunked
80
+ body:
81
+ encoding: ASCII-8BIT
82
+ string: '{"id":"a001a000001LFgMAAW","success":true,"errors":[]}'
83
+ http_version:
84
+ recorded_at: Wed, 01 Apr 2015 17:51:24 GMT
85
+ - request:
86
+ method: get
87
+ uri: https://<host>/services/data/v26.0/query?q=select%20Id,%20SystemModstamp,%20Name,%20Example_Field__c%20from%20CustomObject__c%20where%20Id%20=%20%27a001a000001LFgMAAW%27%20and%20Visible__c%20=%20TRUE
88
+ body:
89
+ encoding: US-ASCII
90
+ string: ''
91
+ headers:
92
+ User-Agent:
93
+ - Faraday v0.9.1
94
+ Authorization:
95
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
96
+ Accept-Encoding:
97
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
98
+ Accept:
99
+ - "*/*"
100
+ response:
101
+ status:
102
+ code: 200
103
+ message: OK
104
+ headers:
105
+ Date:
106
+ - Wed, 01 Apr 2015 17:51:25 GMT
107
+ Set-Cookie:
108
+ - BrowserId=YzZvI_D3ShuJoLZb3ROxkQ;Path=/;Domain=.salesforce.com;Expires=Sun,
109
+ 31-May-2015 17:51:25 GMT
110
+ Expires:
111
+ - Thu, 01 Jan 1970 00:00:00 GMT
112
+ Sforce-Limit-Info:
113
+ - api-usage=17/15000
114
+ Content-Type:
115
+ - application/json;charset=UTF-8
116
+ Transfer-Encoding:
117
+ - chunked
118
+ body:
119
+ encoding: ASCII-8BIT
120
+ string: '{"totalSize":0,"done":true,"records":[]}'
121
+ http_version:
122
+ recorded_at: Wed, 01 Apr 2015 17:51:25 GMT
123
+ - request:
124
+ method: delete
125
+ uri: https://<host>/services/data/v26.0/sobjects/CustomObject__c/a001a000001LFgMAAW
126
+ body:
127
+ encoding: US-ASCII
128
+ string: ''
129
+ headers:
130
+ User-Agent:
131
+ - Faraday v0.9.1
132
+ Authorization:
133
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
134
+ Accept-Encoding:
135
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
136
+ Accept:
137
+ - "*/*"
138
+ response:
139
+ status:
140
+ code: 204
141
+ message: No Content
142
+ headers:
143
+ Date:
144
+ - Wed, 01 Apr 2015 17:51:26 GMT
145
+ Set-Cookie:
146
+ - BrowserId=KChk1bwkRkeQl0fwoxj5TQ;Path=/;Domain=.salesforce.com;Expires=Sun,
147
+ 31-May-2015 17:51:26 GMT
148
+ Expires:
149
+ - Thu, 01 Jan 1970 00:00:00 GMT
150
+ Sforce-Limit-Info:
151
+ - api-usage=17/15000
152
+ body:
153
+ encoding: UTF-8
154
+ string: ''
155
+ http_version:
156
+ recorded_at: Wed, 01 Apr 2015 17:51:26 GMT
157
+ recorded_with: VCR 2.9.3
@@ -0,0 +1,158 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: post
5
+ uri: https://<host>/services/oauth2/token
6
+ body:
7
+ encoding: US-ASCII
8
+ string: grant_type=password&client_id=<client_id>&client_secret=<client_secret>&username=<username>&password=<password><security_token>
9
+ headers:
10
+ User-Agent:
11
+ - Faraday v0.9.1
12
+ Content-Type:
13
+ - application/x-www-form-urlencoded
14
+ Accept-Encoding:
15
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
16
+ Accept:
17
+ - "*/*"
18
+ response:
19
+ status:
20
+ code: 200
21
+ message: OK
22
+ headers:
23
+ Date:
24
+ - Wed, 01 Apr 2015 17:51:18 GMT
25
+ Set-Cookie:
26
+ - BrowserId=-n50WpbhSAmLOfePSfw1JA;Path=/;Domain=.salesforce.com;Expires=Sun,
27
+ 31-May-2015 17:51:18 GMT
28
+ Expires:
29
+ - Thu, 01 Jan 1970 00:00:00 GMT
30
+ Pragma:
31
+ - no-cache
32
+ Cache-Control:
33
+ - no-cache, no-store
34
+ Content-Type:
35
+ - application/json;charset=UTF-8
36
+ Transfer-Encoding:
37
+ - chunked
38
+ body:
39
+ encoding: ASCII-8BIT
40
+ string: '{"id":"https://login.salesforce.com/id/00D1a000000H3O9EAK/0051a000000UGT8AAO","issued_at":"1427910678934","token_type":"Bearer","instance_url":"https://<host>","signature":"r7U6IsW9cCkVABj4E879KcDbgJZSkrit4swb8PBuwtw=","access_token":"00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW"}'
41
+ http_version:
42
+ recorded_at: Wed, 01 Apr 2015 17:51:19 GMT
43
+ - request:
44
+ method: post
45
+ uri: https://<host>/services/data/v26.0/sobjects/CustomObject__c
46
+ body:
47
+ encoding: UTF-8
48
+ string: '{"Name":"Sample object"}'
49
+ headers:
50
+ User-Agent:
51
+ - Faraday v0.9.1
52
+ Content-Type:
53
+ - application/json
54
+ Authorization:
55
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
56
+ Accept-Encoding:
57
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
58
+ Accept:
59
+ - "*/*"
60
+ response:
61
+ status:
62
+ code: 201
63
+ message: Created
64
+ headers:
65
+ Date:
66
+ - Wed, 01 Apr 2015 17:51:19 GMT
67
+ Set-Cookie:
68
+ - BrowserId=uBlo3fFFSeOgxVD78aQnJg;Path=/;Domain=.salesforce.com;Expires=Sun,
69
+ 31-May-2015 17:51:19 GMT
70
+ Expires:
71
+ - Thu, 01 Jan 1970 00:00:00 GMT
72
+ Sforce-Limit-Info:
73
+ - api-usage=17/15000
74
+ Location:
75
+ - "/services/data/v26.0/sobjects/CustomObject__c/a001a000001LFgHAAW"
76
+ Content-Type:
77
+ - application/json;charset=UTF-8
78
+ Transfer-Encoding:
79
+ - chunked
80
+ body:
81
+ encoding: ASCII-8BIT
82
+ string: '{"id":"a001a000001LFgHAAW","success":true,"errors":[]}'
83
+ http_version:
84
+ recorded_at: Wed, 01 Apr 2015 17:51:20 GMT
85
+ - request:
86
+ method: get
87
+ uri: https://<host>/services/data/v26.0/query?q=select%20Id,%20SystemModstamp,%20Name,%20Example_Field__c%20from%20CustomObject__c%20where%20Id%20=%20%27a001a000001LFgHAAW%27%20and%20Visible__c%20=%20TRUE
88
+ body:
89
+ encoding: US-ASCII
90
+ string: ''
91
+ headers:
92
+ User-Agent:
93
+ - Faraday v0.9.1
94
+ Authorization:
95
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
96
+ Accept-Encoding:
97
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
98
+ Accept:
99
+ - "*/*"
100
+ response:
101
+ status:
102
+ code: 200
103
+ message: OK
104
+ headers:
105
+ Date:
106
+ - Wed, 01 Apr 2015 17:51:20 GMT
107
+ Set-Cookie:
108
+ - BrowserId=0luURef9R7uia6N7fuHh9w;Path=/;Domain=.salesforce.com;Expires=Sun,
109
+ 31-May-2015 17:51:20 GMT
110
+ Expires:
111
+ - Thu, 01 Jan 1970 00:00:00 GMT
112
+ Sforce-Limit-Info:
113
+ - api-usage=18/15000
114
+ Content-Type:
115
+ - application/json;charset=UTF-8
116
+ Transfer-Encoding:
117
+ - chunked
118
+ body:
119
+ encoding: ASCII-8BIT
120
+ string: '{"totalSize":1,"done":true,"records":[{"attributes":{"type":"CustomObject__c","url":"/services/data/v26.0/sobjects/CustomObject__c/a001a000001LFgHAAW"},"Id":"a001a000001LFgHAAW","SystemModstamp":"2015-04-01T17:51:19.000+0000","Name":"Sample
121
+ object","Example_Field__c":null}]}'
122
+ http_version:
123
+ recorded_at: Wed, 01 Apr 2015 17:51:21 GMT
124
+ - request:
125
+ method: delete
126
+ uri: https://<host>/services/data/v26.0/sobjects/CustomObject__c/a001a000001LFgHAAW
127
+ body:
128
+ encoding: US-ASCII
129
+ string: ''
130
+ headers:
131
+ User-Agent:
132
+ - Faraday v0.9.1
133
+ Authorization:
134
+ - OAuth 00D1a000000H3O9!AQ4AQKZwdgw8XRPQOd9_ipgseq9yxNqcklYDcsxnqhIM56FN53.IU986f9x29rxVXv5E_w_ReuA_8Q2P_TTVjLPBPmxzVeiW
135
+ Accept-Encoding:
136
+ - gzip;q=1.0,deflate;q=0.6,identity;q=0.3
137
+ Accept:
138
+ - "*/*"
139
+ response:
140
+ status:
141
+ code: 204
142
+ message: No Content
143
+ headers:
144
+ Date:
145
+ - Wed, 01 Apr 2015 17:51:21 GMT
146
+ Set-Cookie:
147
+ - BrowserId=WdYv53V1RZqLRR4JQ5mc5A;Path=/;Domain=.salesforce.com;Expires=Sun,
148
+ 31-May-2015 17:51:21 GMT
149
+ Expires:
150
+ - Thu, 01 Jan 1970 00:00:00 GMT
151
+ Sforce-Limit-Info:
152
+ - api-usage=17/15000
153
+ body:
154
+ encoding: UTF-8
155
+ string: ''
156
+ http_version:
157
+ recorded_at: Wed, 01 Apr 2015 17:51:22 GMT
158
+ recorded_with: VCR 2.9.3
@@ -6,17 +6,28 @@ describe Restforce::DB::Configuration do
6
6
  let(:configuration) { Restforce::DB::Configuration.new }
7
7
 
8
8
  describe "#load" do
9
- before do
10
- configuration.load(secrets)
9
+
10
+ describe "when all configurations are supplied" do
11
+ before do
12
+ configuration.load(secrets)
13
+ end
14
+
15
+ it "loads the credentials from a passed hash" do
16
+ expect(configuration.username).to_equal secrets["username"]
17
+ expect(configuration.password).to_equal secrets["password"]
18
+ expect(configuration.security_token).to_equal secrets["security_token"]
19
+ expect(configuration.client_id).to_equal secrets["client_id"]
20
+ expect(configuration.client_secret).to_equal secrets["client_secret"]
21
+ expect(configuration.host).to_equal secrets["host"]
22
+ end
11
23
  end
12
24
 
13
- it "loads the credentials from a passed hash" do
14
- expect(configuration.username).to_equal secrets["username"]
15
- expect(configuration.password).to_equal secrets["password"]
16
- expect(configuration.security_token).to_equal secrets["security_token"]
17
- expect(configuration.client_id).to_equal secrets["client_id"]
18
- expect(configuration.client_secret).to_equal secrets["client_secret"]
19
- expect(configuration.host).to_equal secrets["host"]
25
+ describe "when the loaded configuration is missing one or more keys" do
26
+ let(:secrets) { {} }
27
+
28
+ it "raises an error" do
29
+ expect(-> { configuration.load(secrets) }).to_raise(ArgumentError)
30
+ end
20
31
  end
21
32
  end
22
33
 
@@ -41,5 +41,38 @@ describe Restforce::DB::RecordTypes::Salesforce do
41
41
  it "returns nil when no matching record exists" do
42
42
  expect(record_type.find("a001a000001E1vFAKE")).to_be_nil
43
43
  end
44
+
45
+ describe "given a set of mapping conditions" do
46
+ let(:conditions) { ["Visible__c = TRUE"] }
47
+
48
+ describe "when a record meets the conditions" do
49
+
50
+ it "finds the record" do
51
+ expect(record_type.find(id)).to_be_instance_of Restforce::DB::Instances::Salesforce
52
+ end
53
+ end
54
+
55
+ describe "when a record does not meet the conditions" do
56
+ let(:id) { Salesforce.create!(salesforce_model, "Visible__c" => false) }
57
+
58
+ it "does not find the record" do
59
+ expect(record_type.find(id)).to_be_nil
60
+ end
61
+ end
62
+ end
44
63
  end
64
+
65
+ describe "#each", :vcr do
66
+ let(:id) { Salesforce.create!(salesforce_model) }
67
+ before { id }
68
+
69
+ # Restforce::DB::RecordType::Salesforce actually implements Enumerable, so
70
+ # we're just going with a trivially testable portion of the Enumerable API.
71
+ it "loops through the existing records in Salesforce" do
72
+ record = record_type.first
73
+ expect(record).to_be_instance_of(Restforce::DB::Instances::Salesforce)
74
+ expect(record.id).to_equal(id)
75
+ end
76
+ end
77
+
45
78
  end
@@ -17,6 +17,7 @@ def mappings!
17
17
  let(:salesforce_model) { "CustomObject__c" }
18
18
  let(:fields) { { name: "Name", example: "Example_Field__c" } }
19
19
  let(:associations) { {} }
20
+ let(:conditions) { [] }
20
21
  let!(:mapping) do
21
22
  Restforce::DB::Mapping.new(
22
23
  database_model,
@@ -24,6 +25,7 @@ def mappings!
24
25
  root: true,
25
26
  fields: fields,
26
27
  associations: associations,
28
+ conditions: conditions,
27
29
  )
28
30
  end
29
31
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: restforce-db
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.4
4
+ version: 0.3.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andrew Horner
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2015-03-31 00:00:00.000000000 Z
11
+ date: 2015-04-01 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activerecord
@@ -242,7 +242,10 @@ files:
242
242
  - test/cassettes/Restforce_DB_Instances_Salesforce/_update_/updates_the_record_in_Salesforce_with_the_passed_attributes.yml
243
243
  - test/cassettes/Restforce_DB_RecordTypes_Salesforce/_create_/creates_a_record_in_Salesforce_from_the_passed_database_record_s_attributes.yml
244
244
  - test/cassettes/Restforce_DB_RecordTypes_Salesforce/_create_/updates_the_database_record_with_the_Salesforce_record_s_ID.yml
245
+ - test/cassettes/Restforce_DB_RecordTypes_Salesforce/_each/loops_through_the_existing_records_in_Salesforce.yml
245
246
  - test/cassettes/Restforce_DB_RecordTypes_Salesforce/_find/finds_existing_records_in_Salesforce.yml
247
+ - test/cassettes/Restforce_DB_RecordTypes_Salesforce/_find/given_a_set_of_mapping_conditions/when_a_record_does_not_meet_the_conditions/does_not_find_the_record.yml
248
+ - test/cassettes/Restforce_DB_RecordTypes_Salesforce/_find/given_a_set_of_mapping_conditions/when_a_record_meets_the_conditions/finds_the_record.yml
246
249
  - test/cassettes/Restforce_DB_RecordTypes_Salesforce/_find/returns_nil_when_no_matching_record_exists.yml
247
250
  - test/cassettes/Restforce_DB_Synchronizer/_run/given_a_Salesforce_record_with_an_associated_database_record/when_synchronization_is_stale/updates_the_database_record.yml
248
251
  - test/cassettes/Restforce_DB_Synchronizer/_run/given_a_Salesforce_record_with_an_associated_database_record/when_synchronization_is_up-to-date/does_not_update_the_database_record.yml