netsuite_rails 0.1.0 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (34) hide show
  1. data/.gitignore +3 -0
  2. data/.travis.yml +3 -0
  3. data/Gemfile +17 -7
  4. data/README.md +9 -4
  5. data/lib/netsuite_rails/configuration.rb +3 -1
  6. data/lib/netsuite_rails/list_sync/poll_manager.rb +30 -0
  7. data/lib/netsuite_rails/list_sync.rb +2 -2
  8. data/lib/netsuite_rails/netsuite_rails.rb +13 -3
  9. data/lib/netsuite_rails/poll_timestamp.rb +5 -0
  10. data/lib/netsuite_rails/{poll_manager.rb → poll_trigger.rb} +18 -3
  11. data/lib/netsuite_rails/record_sync/poll_manager.rb +186 -0
  12. data/lib/netsuite_rails/record_sync/pull_manager.rb +10 -137
  13. data/lib/netsuite_rails/record_sync/push_manager.rb +59 -21
  14. data/lib/netsuite_rails/record_sync.rb +142 -140
  15. data/lib/netsuite_rails/spec/spec_helper.rb +34 -6
  16. data/lib/netsuite_rails/sync_trigger.rb +80 -75
  17. data/lib/netsuite_rails/tasks/netsuite.rb +26 -30
  18. data/lib/netsuite_rails/url_helper.rb +12 -3
  19. data/netsuite_rails.gemspec +3 -3
  20. data/spec/models/poll_manager_spec.rb +45 -0
  21. data/spec/models/poll_trigger_spec.rb +26 -0
  22. data/spec/models/record_sync/push_manager_spec.rb +0 -0
  23. data/spec/models/spec_helper_spec.rb +29 -0
  24. data/spec/models/sync_trigger_spec.rb +62 -0
  25. data/spec/models/url_helper_spec.rb +23 -0
  26. data/spec/spec_helper.rb +17 -1
  27. data/spec/support/config/database.yml +11 -0
  28. data/spec/support/dynamic_models/class_builder.rb +48 -0
  29. data/spec/support/dynamic_models/model_builder.rb +83 -0
  30. data/spec/support/example_models.rb +31 -0
  31. data/spec/support/netsuite_rails.rb +1 -0
  32. data/spec/support/test_application.rb +55 -0
  33. metadata +36 -10
  34. data/lib/netsuite_rails/list_sync/pull_manager.rb +0 -33
@@ -4,18 +4,27 @@ module NetSuiteRails
4
4
  class PushManager
5
5
  class << self
6
6
 
7
- def push(local_record, opts)
7
+ def push(local_record, opts = {})
8
8
  # TODO check to see if anything is changed before moving forward
9
9
  # if changes_keys.blank? && local_record.netsuite_manual_fields
10
10
 
11
- netsuite_record = build_netsuite_record(local_record)
11
+ if opts[:modified_fields]
12
+ # if Array, we need to convert info fields hash based on the record definition
13
+ if opts[:modified_fields].is_a?(Array)
14
+ opts[:modified_fields] = all_netsuite_fields(local_record).select { |k,v| opts[:modified_fields].include?(k) }
15
+ end
16
+ else
17
+ opts[:modified_fields] = modified_local_fields(local_record)
18
+ end
19
+
20
+ netsuite_record = build_netsuite_record(local_record, opts)
12
21
 
13
22
  local_record.netsuite_execute_callbacks(local_record.class.before_netsuite_push, netsuite_record)
14
23
 
15
24
  if !local_record.new_netsuite_record?
16
- push_update(local_record, netsuite_record)
25
+ push_update(local_record, netsuite_record, opts)
17
26
  else
18
- push_add(local_record, netsuite_record)
27
+ push_add(local_record, netsuite_record, opts)
19
28
  end
20
29
 
21
30
  # :aggressive is for custom fields which are based on input – need pull updated values after
@@ -30,7 +39,7 @@ module NetSuiteRails
30
39
  true
31
40
  end
32
41
 
33
- def push_add(local_record, netsuite_record)
42
+ def push_add(local_record, netsuite_record, opts = {})
34
43
  if netsuite_record.add
35
44
  # update_column to avoid triggering another save
36
45
  local_record.update_column(:netsuite_id, netsuite_record.internal_id)
@@ -40,17 +49,17 @@ module NetSuiteRails
40
49
  end
41
50
  end
42
51
 
43
- def push_update(local_record, netsuite_record)
52
+ def push_update(local_record, netsuite_record, opts = {})
44
53
  # build change hash to limit the number of fields pushed to NS on change
45
54
  # NS could have logic which could change field functionality depending on
46
55
  # input data; it's safest to limit the number of field changes pushed to NS
47
56
 
48
57
  custom_field_list = local_record.netsuite_field_map[:custom_field_list] || {}
49
- all_field_list = eligible_local_fields(local_record)
58
+ modified_fields_list = opts[:modified_fields]
50
59
 
51
60
  update_list = {}
52
61
 
53
- all_field_list.each do |local_field, netsuite_field|
62
+ modified_fields_list.each do |local_field, netsuite_field|
54
63
  if custom_field_list.keys.include?(local_field)
55
64
  # if custom field has changed, mark and copy over customFieldList later
56
65
  update_list[:custom_field_list] = true
@@ -87,15 +96,21 @@ module NetSuiteRails
87
96
  end
88
97
  end
89
98
 
90
- def build_netsuite_record(local_record)
99
+ def build_netsuite_record(local_record, opts = {})
91
100
  netsuite_record = build_netsuite_record_reference(local_record)
92
101
 
93
102
  # TODO need to normalize datetime fields
94
103
 
95
- all_field_list = eligible_local_fields(local_record)
104
+ all_field_list = opts[:modified_fields]
96
105
  custom_field_list = local_record.netsuite_field_map[:custom_field_list] || {}
97
106
  field_hints = local_record.netsuite_field_hints
98
107
 
108
+ reflections = if NetSuiteRails.rails4?
109
+ local_record.class.reflections
110
+ else
111
+ local_record.reflections
112
+ end
113
+
99
114
  all_field_list.each do |local_field, netsuite_field|
100
115
  # allow Procs as field mapping in the record definition for custom mapping
101
116
  if netsuite_field.is_a?(Proc)
@@ -105,7 +120,7 @@ module NetSuiteRails
105
120
 
106
121
  # TODO pretty sure this will break if we are dealing with has_many
107
122
 
108
- netsuite_field_value = if local_record.reflections.has_key?(local_field)
123
+ netsuite_field_value = if reflections.has_key?(local_field)
109
124
  if (remote_internal_id = local_record.send(local_field).try(:netsuite_id)).present?
110
125
  { internal_id: remote_internal_id }
111
126
  else
@@ -145,20 +160,24 @@ module NetSuiteRails
145
160
  netsuite_record
146
161
  end
147
162
 
148
- def eligible_local_fields(local_record)
149
- custom_field_list = local_record.netsuite_field_map[:custom_field_list] || {}
150
- all_field_list = local_record.netsuite_field_map.except(:custom_field_list) || {}
151
-
152
- all_field_list.merge!(custom_field_list)
163
+ def modified_local_fields(local_record)
164
+ synced_netsuite_fields = all_netsuite_fields(local_record)
153
165
 
154
166
  changed_keys = changed_attributes(local_record)
155
167
 
156
168
  # filter out unchanged keys when updating record
157
169
  unless local_record.new_netsuite_record?
158
- all_field_list.select! { |k,v| changed_keys.include?(k) }
170
+ synced_netsuite_fields.select! { |k,v| changed_keys.include?(k) }
159
171
  end
160
172
 
161
- all_field_list
173
+ synced_netsuite_fields
174
+ end
175
+
176
+ def all_netsuite_fields(local_record)
177
+ custom_netsuite_field_list = local_record.netsuite_field_map[:custom_field_list] || {}
178
+ standard_netsuite_field_list = local_record.netsuite_field_map.except(:custom_field_list) || {}
179
+
180
+ custom_netsuite_field_list.merge(standard_netsuite_field_list)
162
181
  end
163
182
 
164
183
  def changed_attributes(local_record)
@@ -167,13 +186,32 @@ module NetSuiteRails
167
186
 
168
187
  # TODO think about has_many / join table changes
169
188
 
170
- association_field_key_mapping = local_record.reflections.values.reject(&:collection?).inject({}) do |h, a|
171
- h[a.association_foreign_key.to_sym] = a.name
189
+ reflections = if NetSuiteRails.rails4?
190
+ local_record.class.reflections
191
+ else
192
+ local_record.reflections
193
+ end
194
+
195
+ association_field_key_mapping = reflections.values.reject(&:collection?).inject({}) do |h, a|
196
+ begin
197
+ h[a.association_foreign_key.to_sym] = a.name
198
+ rescue Exception => e
199
+ # occurs when `has_one through:` exists on a record but `through` is not a valid reference
200
+ Rails.logger.error "NetSuite: error detecting foreign key #{a.name}"
201
+ end
202
+
172
203
  h
173
204
  end
174
205
 
206
+ changed_attributes_keys = local_record.changed_attributes.keys
207
+
208
+ # TODO documentation about serialized values
209
+ changed_attributes_keys += local_record.serialized_attributes.keys.map do |k|
210
+ local_record.send(k.to_sym).keys.map(&:to_s)
211
+ end.flatten
212
+
175
213
  # convert relationship symbols from :object_id to :object
176
- local_record.changed_attributes.keys.map do |k|
214
+ changed_attributes_keys.map do |k|
177
215
  association_field_key_mapping[k.to_sym] || k.to_sym
178
216
  end
179
217
  end
@@ -2,72 +2,81 @@ module NetSuiteRails
2
2
  module RecordSync
3
3
 
4
4
  def self.included(klass)
5
+ klass.class_eval do
6
+ class_attribute :netsuite_settings
7
+
8
+ self.netsuite_settings = {
9
+ before_netsuite_push: [],
10
+ after_netsuite_push: [],
11
+ after_netsuite_pull: [],
12
+
13
+ netsuite_sync: :read,
14
+ netsuite_field_map: {},
15
+ netsuite_field_hints: {},
16
+ netsuite_record_class: nil,
17
+ }
18
+
19
+ cattr_accessor :netsuite_custom_record_type_id
20
+ cattr_accessor :netsuite_sync_options
21
+ end
22
+
5
23
  klass.send(:extend, ClassMethods)
24
+ klass.send(:include, InstanceMethods)
6
25
 
7
26
  SyncTrigger.attach(klass)
8
- PollManager.attach(klass)
27
+ PollTrigger.attach(klass)
9
28
  end
10
29
 
11
30
  module ClassMethods
12
31
  def netsuite_poll(opts = {})
13
- RecordSync::PullManager.poll(self, opts)
32
+ RecordSync::PollManager.poll(self, opts)
14
33
  end
15
34
 
16
35
  attr_accessor :netsuite_custom_record_type_id
17
36
  attr_accessor :netsuite_sync_options
18
- attr_accessor :netsuite_credentials
19
37
 
20
38
  # TODO is there a better way to implement callback chains?
21
39
  # https://github.com/rails/rails/blob/0c0f278ab20f3042cdb69604166e18a61f8605ad/activesupport/lib/active_support/callbacks.rb#L491
22
40
 
23
41
  def before_netsuite_push(callback = nil, &block)
24
- @before_netsuite_push ||= []
25
- @before_netsuite_push << (callback || block) if callback || block
26
- @before_netsuite_push
42
+ self.netsuite_settings[:before_netsuite_push] << (callback || block) if callback || block
43
+ self.netsuite_settings[:before_netsuite_push]
27
44
  end
28
45
 
29
46
  def after_netsuite_push(callback = nil, &block)
30
- @after_netsuite_push ||= []
31
- @after_netsuite_push << (callback || block) if callback || block
32
- @after_netsuite_push
47
+ self.netsuite_settings[:after_netsuite_push] << (callback || block) if callback || block
48
+ self.netsuite_settings[:after_netsuite_push]
33
49
  end
34
50
 
35
51
  def after_netsuite_pull(callback = nil, &block)
36
- @after_netsuite_pull ||= []
37
- @after_netsuite_pull << (callback || block) if callback || block
38
- @after_netsuite_pull
52
+ self.netsuite_settings[:after_netsuite_pull] << (callback || block) if callback || block
53
+ self.netsuite_settings[:after_netsuite_pull]
39
54
  end
40
55
 
41
56
  def netsuite_field_map(field_mapping = nil)
42
- if field_mapping.nil?
43
- @netsuite_field_map ||= {}
44
- else
45
- @netsuite_field_map = field_mapping
57
+ if !field_mapping.nil?
58
+ self.netsuite_settings[:netsuite_field_map] = field_mapping
46
59
  end
47
60
 
48
- @netsuite_field_map
49
- end
50
-
51
- def netsuite_local_fields
52
- @netsuite_field_map.except(:custom_field_list).keys + (@netsuite_field_map[:custom_field_list] || {}).keys
61
+ self.netsuite_settings[:netsuite_field_map]
53
62
  end
54
63
 
55
64
  def netsuite_field_hints(list = nil)
56
- if list.nil?
57
- @netsuite_field_hints ||= {}
58
- else
59
- @netsuite_field_hints = list
65
+ if !list.nil?
66
+ self.netsuite_settings[:netsuite_field_hints] = list
60
67
  end
68
+
69
+ self.netsuite_settings[:netsuite_field_hints]
61
70
  end
62
71
 
63
72
  # TODO persist type for CustomRecordRef
64
73
  def netsuite_record_class(record_class = nil, custom_record_type_id = nil)
65
- if record_class.nil?
66
- @netsuite_record_class
67
- else
68
- @netsuite_record_class = record_class
69
- @netsuite_custom_record_type_id = custom_record_type_id
74
+ if !record_class.nil?
75
+ self.netsuite_settings[:netsuite_record_class] = record_class
76
+ self.netsuite_custom_record_type_id = custom_record_type_id
70
77
  end
78
+
79
+ self.netsuite_settings[:netsuite_record_class]
71
80
  end
72
81
 
73
82
  # there is a model level of this method in order to be based on the model level record class
@@ -75,160 +84,153 @@ module NetSuiteRails
75
84
  self.netsuite_record_class == NetSuite::Records::CustomRecord
76
85
  end
77
86
 
78
- # :read_only, :aggressive (push & update on save), :write_only, :read_write
87
+ # :read, :aggressive (push & update on save), :write_only, :read_write
79
88
  def netsuite_sync(flag = nil, opts = {})
80
- if flag.nil?
81
- @netsuite_sync_options ||= {}
82
- @netsuite_sync ||= :read_only
83
- else
84
- @netsuite_sync = flag
85
- @netsuite_sync_options = opts
89
+ if !flag.nil?
90
+ self.netsuite_sync_options = opts
91
+ self.netsuite_settings[:netsuite_sync] = flag
86
92
  end
93
+
94
+ self.netsuite_settings[:netsuite_sync]
87
95
  end
88
96
  end
89
97
 
90
- attr_accessor :netsuite_manual_fields
98
+ module InstanceMethods
99
+ attr_accessor :netsuite_manual_fields
91
100
 
92
- # these methods are here for easy model override
101
+ # these methods are here for easy model override
93
102
 
94
- def netsuite_sync_options
95
- self.class.netsuite_sync_options
96
- end
97
-
98
- def netsuite_sync
99
- self.class.netsuite_sync
100
- end
103
+ def netsuite_sync_options
104
+ self.class.netsuite_sync_options
105
+ end
101
106
 
102
- def netsuite_record_class
103
- self.class.netsuite_record_class
104
- end
107
+ def netsuite_sync
108
+ self.class.netsuite_sync
109
+ end
105
110
 
106
- def netsuite_field_map
107
- self.class.netsuite_field_map
108
- end
111
+ def netsuite_record_class
112
+ self.class.netsuite_record_class
113
+ end
109
114
 
110
- def netsuite_field_hints
111
- self.class.netsuite_field_hints
112
- end
115
+ def netsuite_field_map
116
+ self.class.netsuite_field_map
117
+ end
113
118
 
114
- # assumes netsuite_id field on activerecord
119
+ def netsuite_field_hints
120
+ self.class.netsuite_field_hints
121
+ end
115
122
 
116
- def netsuite_pulling?
117
- @netsuite_pulling ||= false
118
- end
123
+ # assumes netsuite_id field on activerecord
119
124
 
120
- def netsuite_pulled?
121
- @netsuite_pulled ||= false
122
- end
125
+ def netsuite_pulling?
126
+ @netsuite_pulling ||= false
127
+ end
123
128
 
124
- def netsuite_pull
125
- netsuite_extract_from_record(netsuite_pull_record)
126
- end
129
+ def netsuite_pulled?
130
+ @netsuite_pulled ||= false
131
+ end
127
132
 
128
- def netsuite_pull_record
129
- if netsuite_custom_record?
130
- NetSuite::Records::CustomRecord.get(
131
- internal_id: self.netsuite_id,
132
- type_id: self.class.netsuite_custom_record_type_id
133
- )
134
- else
135
- self.netsuite_record_class.get(self.netsuite_id)
133
+ def netsuite_pull
134
+ netsuite_extract_from_record(netsuite_pull_record)
136
135
  end
137
- end
138
136
 
139
- def netsuite_push(opts = {})
140
- NetSuiteRails::RecordSync::PushManager.push(self, opts)
141
- end
137
+ def netsuite_pull_record
138
+ if netsuite_custom_record?
139
+ NetSuite::Records::CustomRecord.get(
140
+ internal_id: self.netsuite_id,
141
+ type_id: self.class.netsuite_custom_record_type_id
142
+ )
143
+ else
144
+ self.netsuite_record_class.get(self.netsuite_id)
145
+ end
146
+ end
142
147
 
143
- def netsuite_extract_from_record(netsuite_record)
144
- @netsuite_pulling = true
148
+ def netsuite_push(opts = {})
149
+ NetSuiteRails::RecordSync::PushManager.push(self, opts)
150
+ end
145
151
 
146
- field_hints = self.netsuite_field_hints
152
+ def netsuite_extract_from_record(netsuite_record)
153
+ @netsuite_pulling = true
147
154
 
148
- custom_field_list = self.netsuite_field_map[:custom_field_list] || {}
155
+ field_hints = self.netsuite_field_hints
149
156
 
150
- all_field_list = self.netsuite_field_map.except(:custom_field_list) || {}
151
- all_field_list.merge!(custom_field_list)
157
+ custom_field_list = self.netsuite_field_map[:custom_field_list] || {}
152
158
 
153
- # self.netsuite_normalize_datetimes(:pull)
159
+ all_field_list = self.netsuite_field_map.except(:custom_field_list) || {}
160
+ all_field_list.merge!(custom_field_list)
154
161
 
155
- # handle non-collection associations
156
- association_keys = self.reflections.values.reject(&:collection?).map(&:name)
162
+ # self.netsuite_normalize_datetimes(:pull)
157
163
 
158
- all_field_list.each do |local_field, netsuite_field|
159
- is_custom_field = custom_field_list.keys.include?(local_field)
164
+ # handle non-collection associations
165
+ association_keys = self.reflections.values.reject(&:collection?).map(&:name)
160
166
 
161
- if netsuite_field.is_a?(Proc)
162
- netsuite_field.call(self, netsuite_record, :pull)
163
- next
164
- end
167
+ all_field_list.each do |local_field, netsuite_field|
168
+ is_custom_field = custom_field_list.keys.include?(local_field)
165
169
 
166
- field_value = if is_custom_field
167
- netsuite_record.custom_field_list.send(netsuite_field).value rescue ""
168
- else
169
- netsuite_record.send(netsuite_field)
170
- end
170
+ if netsuite_field.is_a?(Proc)
171
+ netsuite_field.call(self, netsuite_record, :pull)
172
+ next
173
+ end
171
174
 
172
- if field_value.blank?
173
- # TODO possibly nil out the local value?
174
- next
175
- end
175
+ field_value = if is_custom_field
176
+ netsuite_record.custom_field_list.send(netsuite_field).value rescue ""
177
+ else
178
+ netsuite_record.send(netsuite_field)
179
+ end
176
180
 
177
- if association_keys.include?(local_field)
178
- field_value = self.reflections[local_field].klass.where(netsuite_id: field_value.internal_id).first_or_initialize
179
- elsif is_custom_field
180
- # TODO I believe this only handles a subset of all the possibly CustomField values
181
- if field_value.present? && field_value.is_a?(Hash) && field_value.has_key?(:name)
182
- field_value = field_value[:name]
181
+ if field_value.blank?
182
+ # TODO possibly nil out the local value?
183
+ next
183
184
  end
184
185
 
185
- if field_value.present? && field_value.is_a?(NetSuite::Records::CustomRecordRef)
186
- field_value = field_value.attributes[:name]
186
+ if association_keys.include?(local_field)
187
+ field_value = self.reflections[local_field].klass.where(netsuite_id: field_value.internal_id).first_or_initialize
188
+ elsif is_custom_field
189
+ field_value = NetSuiteRails::RecordSync::PullManager.extract_custom_field_value(field_value)
190
+ else
191
+ # then it's not a custom field
187
192
  end
188
- else
189
- # then it's not a custom field
190
- end
191
193
 
192
- # TODO should we just check for nil? vs present?
194
+ # TODO should we just check for nil? vs present?
193
195
 
194
- # TODO should be moved to Transformations with a direction flag
195
- if field_hints.has_key?(local_field) && field_value.present?
196
- case field_hints[local_field]
197
- when :datetime
198
- field_value = field_value.change(offset: "00:00") - (Time.zone.utc_offset / 3600).hours + (8 + NetSuiteRails::Configuration.netsuite_instance_time_zone_offset).hours
196
+ # TODO should be moved to Transformations with a direction flag
197
+ if field_hints.has_key?(local_field) && field_value.present?
198
+ case field_hints[local_field]
199
+ when :datetime
200
+ field_value = field_value.change(offset: "00:00") - (Time.zone.utc_offset / 3600).hours + (8 + NetSuiteRails::Configuration.netsuite_instance_time_zone_offset).hours
201
+ end
199
202
  end
200
- end
201
203
 
202
- self.send(:"#{local_field}=", field_value)
203
- end
204
+ self.send(:"#{local_field}=", field_value)
205
+ end
204
206
 
205
- netsuite_execute_callbacks(self.class.after_netsuite_pull, netsuite_record)
207
+ netsuite_execute_callbacks(self.class.after_netsuite_pull, netsuite_record)
206
208
 
207
- @netsuite_pulling = false
208
- @netsuite_pulled = true
209
+ @netsuite_pulling = false
210
+ @netsuite_pulled = true
211
+ end
209
212
 
210
- # return netsuite record for debugging
211
- netsuite_record
212
- end
213
213
 
214
- def new_netsuite_record?
215
- self.netsuite_id.blank?
216
- end
214
+ def new_netsuite_record?
215
+ self.netsuite_id.blank?
216
+ end
217
217
 
218
- def netsuite_custom_record?
219
- self.netsuite_record_class == NetSuite::Records::CustomRecord
220
- end
218
+ def netsuite_custom_record?
219
+ self.netsuite_record_class == NetSuite::Records::CustomRecord
220
+ end
221
221
 
222
- # TODO this should be protected; it needs to be pushed down to the Push/Pull manager level
222
+ # TODO this should be protected; it needs to be pushed down to the Push/Pull manager level
223
223
 
224
- def netsuite_execute_callbacks(list, record)
225
- list.each do |callback|
226
- if callback.is_a?(Symbol)
227
- self.send(callback, record)
228
- else
229
- instance_exec(record, &callback)
224
+ def netsuite_execute_callbacks(list, record)
225
+ list.each do |callback|
226
+ if callback.is_a?(Symbol)
227
+ self.send(callback, record)
228
+ else
229
+ instance_exec(record, &callback)
230
+ end
230
231
  end
231
232
  end
233
+
232
234
  end
233
235
 
234
236
  end
@@ -10,15 +10,26 @@ module NetSuiteRails::TestHelpers
10
10
  if stamp.nil?
11
11
  @netsuite_timestamp ||= (Time.now - (60 * 2)).to_datetime
12
12
  else
13
- @netsuite_timestamp ||= stamp
13
+ @netsuite_timestamp = stamp
14
14
  end
15
15
  end
16
16
 
17
17
  def get_last_netsuite_object(record)
18
- search = record.netsuite_record_class.search({
18
+ # TODO support passing custom record ref
19
+
20
+ if record.is_a?(Class)
21
+ record_class = record
22
+ is_custom_record = false
23
+ else
24
+ record_class = record.netsuite_record_class
25
+ is_custom_record = record.netsuite_custom_record?
26
+ end
27
+
28
+ search = record_class.search({
19
29
  criteria: {
20
30
  basic:
21
- if record.netsuite_custom_record?
31
+ (
32
+ if is_custom_record
22
33
  [
23
34
  {
24
35
  field: 'recType',
@@ -39,18 +50,35 @@ module NetSuiteRails::TestHelpers
39
50
  value: netsuite_timestamp
40
51
  }
41
52
  ]
53
+ end +
54
+
55
+ if record_class == NetSuite::Records::SalesOrder
56
+ [
57
+ {
58
+ field: 'type',
59
+ operator: 'anyOf',
60
+ value: [ '_salesOrder' ]
61
+ }
62
+ ]
63
+ else
64
+ []
42
65
  end
66
+ )
43
67
  }
44
68
  })
45
69
 
46
- if record.netsuite_custom_record?
70
+ if is_custom_record
47
71
  NetSuite::Records::CustomRecord.get(
48
72
  internal_id: search.results.first.internal_id.to_i,
49
73
  type_id: record.class.netsuite_custom_record_type_id
50
74
  )
51
75
  else
52
- record.netsuite_record_class.get(search.results.first.internal_id.to_i)
76
+ record_class.get(search.results.first.internal_id.to_i)
53
77
  end
54
78
  end
55
79
 
56
- end
80
+ end
81
+
82
+ RSpec.configure do |config|
83
+ config.include NetSuiteRails::TestHelpers, type: :feature
84
+ end