rsr_group 1.8.0 → 2.0.1

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: fad2958461833a387cb30e337cc04bbefb1a674a
4
- data.tar.gz: b72595cc6a0dbc0016728fb3519d28e03ff01d94
3
+ metadata.gz: 27991f59b6bc1ffd9323f289032eb43c2cb02eff
4
+ data.tar.gz: b51ac996718c674f4a3e635780e35a7cea841793
5
5
  SHA512:
6
- metadata.gz: 581611d9c64fec310a2d8b5e492fb44ac5507f5bc14ef758dc8352c8863066f2dab397fc5c5092f8da85fbac76d0a7e6ea18454c30e52dc0538deb3e6cdb3cc3
7
- data.tar.gz: 590fb42cc224d76ca798064a050077c47eb23c691fb064eabfa50d76e4585925e3ae614146cea4027e1214197e7511487095382d1c8b551526e34d31c587f57c
6
+ metadata.gz: d9b6f14459886bbc9f3d94ff15d24e67c7c6627877b71298f75fc3dd2dbc6476d70f53df80a2c9c0259eff6ab2fe735bfafb5b6bdfbeaeed218af8eccf2a3615
7
+ data.tar.gz: 6be675b380406ffad1bd4029d7d20c582c10477b481157d8c9666eba28ae4a81109764b55e8c9c1536381ae1c18e7041993df47a64a6e31548ca05b10ba711cb
data/lib/rsr_group.rb CHANGED
@@ -10,6 +10,7 @@ require 'rsr_group/constants'
10
10
  require 'rsr_group/chunker'
11
11
  require 'rsr_group/data_row'
12
12
  require 'rsr_group/department'
13
+ require 'rsr_group/catalog'
13
14
  require 'rsr_group/inventory'
14
15
  require 'rsr_group/order'
15
16
  require 'rsr_group/order_detail'
@@ -0,0 +1,86 @@
1
+ module RsrGroup
2
+ class Catalog < Base
3
+
4
+ KEYDEALER_DIR = 'keydealer'.freeze
5
+ INVENTORY_DIR = 'ftpdownloads'.freeze
6
+ INVENTORY_FILENAME = 'rsrinventory-new.txt'.freeze
7
+ KEYDEALER_FILENAME = 'rsrinventory-keydlr-new.txt'.freeze
8
+
9
+ def initialize(options = {})
10
+ requires!(options, :username, :password)
11
+
12
+ @options = options
13
+ end
14
+
15
+ def self.all(chunk_size = 15, options = {}, &block)
16
+ requires!(options, :username, :password)
17
+ new(options).all(chunk_size, &block)
18
+ end
19
+
20
+ def all(chunk_size, &block)
21
+ connect(@options) do |ftp|
22
+ begin
23
+ chunker = RsrGroup::Chunker.new(chunk_size)
24
+ csv_tempfile = Tempfile.new
25
+
26
+ if ftp.nlst.include?(KEYDEALER_DIR)
27
+ ftp.chdir(KEYDEALER_DIR)
28
+ ftp.getbinaryfile(KEYDEALER_FILENAME, csv_tempfile.path)
29
+ else
30
+ ftp.chdir(INVENTORY_DIR)
31
+ ftp.getbinaryfile(INVENTORY_FILENAME, csv_tempfile.path)
32
+ end
33
+
34
+ chunker.total_count = File.readlines(csv_tempfile).size
35
+
36
+ CSV.readlines(csv_tempfile, col_sep: ';', quote_char: "\x00").to_enum.with_index(1).each do |row, current_line|
37
+ if chunker.is_full?
38
+ yield(chunker.chunk)
39
+
40
+ chunker.reset
41
+ elsif chunker.is_complete?
42
+ yield(chunker.chunk)
43
+
44
+ break
45
+ else
46
+ chunker.add(process_row(row))
47
+ end
48
+ end
49
+ end
50
+
51
+ csv_tempfile.unlink
52
+ ftp.close
53
+ end
54
+ end
55
+
56
+ private
57
+
58
+ def sanitize(data)
59
+ return data unless data.is_a?(String)
60
+ data.strip
61
+ end
62
+
63
+ def process_row(row)
64
+ {
65
+ upc: sanitize(row[1]),
66
+ item_identifier: sanitize(row[0]),
67
+ name: sanitize(row[2]),
68
+ short_description: sanitize(row[2]),
69
+ category: row[3].nil? ? row[3] : RsrGroup::Department.new(row[3]).name,
70
+ brand: sanitize(row[10]),
71
+ map_price: sanitize(row[72]),
72
+ price: sanitize(row[6]),
73
+ quantity: (Integer(sanitize(row[8])) rescue 0),
74
+ mfg_number: sanitize(row[11]),
75
+ weight: sanitize(row[7]),
76
+ long_description: sanitize(row[13]),
77
+ features: {
78
+ shipping_length: sanitize(row[74]),
79
+ shipping_width: sanitize(row[75]),
80
+ shipping_height: sanitize(row[76])
81
+ }
82
+ }
83
+ end
84
+
85
+ end
86
+ end
@@ -26,9 +26,9 @@ module RsrGroup
26
26
  @name = points[3]
27
27
  @zip = points[4]
28
28
  when :order_detail # 20
29
- get_errors(points[6]) if has_errors && points[6] != "00000"
30
- @quantity = points[3].to_i
31
- @stock_id = points[2]
29
+ get_errors(points[-1]) if has_errors && points[-1] != "00000"
30
+ @quantity = points[3].to_i
31
+ @stock_id = points[2]
32
32
  @shipping_carrier = points[4]
33
33
  @shipping_method = SHIPPING_METHODS[points[5]]
34
34
  when :confirmation_header # 30
@@ -3,281 +3,24 @@ module RsrGroup
3
3
 
4
4
  KEYDEALER_DIR = 'keydealer'.freeze
5
5
  INVENTORY_DIR = 'ftpdownloads'.freeze
6
- INVENTORY_FILENAME = 'rsrinventory-new.txt'.freeze
7
- KEYDEALER_FILENAME = 'rsrinventory-keydlr-new.txt'.freeze
8
6
  QTY_FILENAME = 'IM-QTY-CSV.csv'.freeze
9
7
  MAP_FILENAME = 'retail-map.csv'.freeze
10
8
 
11
9
  def initialize(options = {})
12
10
  requires!(options, :username, :password)
13
- @options = options
14
- end
15
-
16
- def self.all(options = {})
17
- requires!(options, :username, :password)
18
- new(options).all
19
- end
20
-
21
- def self.process_as_chunks(size = 15, options = {}, &block)
22
- requires!(options, :username, :password)
23
- new(options).process_as_chunks(size, &block)
24
- end
25
11
 
26
- def self.map_prices(options = {})
27
- requires!(options, :username, :password)
28
- new(options).map_prices
29
- end
30
-
31
- def self.map_prices_as_chunks(size = 15, options = {}, &block)
32
- requires!(options, :username, :password)
33
- new(options).map_prices_as_chunks(size, &block)
34
- end
35
-
36
- def self.quantities(options = {})
37
- requires!(options, :username, :password)
38
- new(options).quantities
12
+ @options = options
39
13
  end
40
14
 
41
- def self.quantities_as_chunks(size = 15, options = {}, &block)
15
+ def self.all(chunk_size = 15, options = {}, &block)
42
16
  requires!(options, :username, :password)
43
- new(options).quantities_as_chunks(size, &block)
44
- end
45
-
46
- def all
47
- items = []
48
-
49
- connect(@options) do |ftp|
50
- if ftp.nlst.include?(KEYDEALER_DIR)
51
- ftp.chdir(KEYDEALER_DIR)
52
- lines = ftp.gettextfile(KEYDEALER_FILENAME, nil)
53
- else
54
- ftp.chdir(INVENTORY_DIR)
55
- lines = ftp.gettextfile(INVENTORY_FILENAME, nil)
56
- end
57
-
58
- # Use a zero-byte char as `quote_char` since the data has no quote character.
59
- CSV.parse(lines, col_sep: ';', quote_char: "\x00") do |row|
60
- items << {
61
- stock_number: sanitize(row[0]),
62
- upc: sanitize(row[1]),
63
- description: sanitize(row[2]),
64
- department: row[3].nil? ? row[3] : RsrGroup::Department.new(row[3]),
65
- manufacturer_id: sanitize(row[4]),
66
- retail_price: sanitize(row[5]),
67
- regular_price: sanitize(row[6]),
68
- weight: sanitize(row[7]),
69
- quantity: (Integer(sanitize(row[8])) rescue 0),
70
- model: sanitize(row[9]),
71
- manufacturer_name: sanitize(row[10]),
72
- manufacturer_part_number: sanitize(row[11]),
73
- allocated_closeout_deleted: sanitize(row[12]),
74
- description_full: sanitize(row[13]),
75
- image_name: sanitize(row[14]),
76
- restricted_states: {
77
- AK: row[15] == 'Y',
78
- AL: row[16] == 'Y',
79
- AR: row[17] == 'Y',
80
- AZ: row[18] == 'Y',
81
- CA: row[19] == 'Y',
82
- CO: row[20] == 'Y',
83
- CT: row[21] == 'Y',
84
- DC: row[22] == 'Y',
85
- DE: row[23] == 'Y',
86
- FL: row[24] == 'Y',
87
- GA: row[25] == 'Y',
88
- HI: row[26] == 'Y',
89
- IA: row[27] == 'Y',
90
- ID: row[28] == 'Y',
91
- IL: row[29] == 'Y',
92
- IN: row[30] == 'Y',
93
- KS: row[31] == 'Y',
94
- KY: row[32] == 'Y',
95
- LA: row[33] == 'Y',
96
- MA: row[36] == 'Y',
97
- MD: row[37] == 'Y',
98
- ME: row[38] == 'Y',
99
- MI: row[39] == 'Y',
100
- MN: row[40] == 'Y',
101
- MO: row[41] == 'Y',
102
- MS: row[42] == 'Y',
103
- MT: row[43] == 'Y',
104
- NC: row[44] == 'Y',
105
- ND: row[45] == 'Y',
106
- NE: row[46] == 'Y',
107
- NH: row[47] == 'Y',
108
- NJ: row[48] == 'Y',
109
- NM: row[49] == 'Y',
110
- NV: row[50] == 'Y',
111
- NY: row[51] == 'Y',
112
- OH: row[52] == 'Y',
113
- OK: row[53] == 'Y',
114
- OR: row[54] == 'Y',
115
- PA: row[55] == 'Y',
116
- RI: row[56] == 'Y',
117
- SC: row[57] == 'Y',
118
- SD: row[58] == 'Y',
119
- TN: row[59] == 'Y',
120
- TX: row[60] == 'Y',
121
- UT: row[61] == 'Y',
122
- VA: row[62] == 'Y',
123
- VT: row[63] == 'Y',
124
- WA: row[64] == 'Y',
125
- WI: row[65] == 'Y',
126
- WV: row[66] == 'Y',
127
- WY: row[67] == 'Y',
128
- },
129
- ground_shipping_only: row[68] == 'Y',
130
- adult_signature_required: row[69] == 'Y',
131
- blocked_from_drop_ship: row[70] == 'Y',
132
- date_entered: row[71].nil? ? row[71] : Date.strptime(row[71], '%Y%m%d'),
133
- retail_map: sanitize(row[72]),
134
- image_disclaimer: row[73] == 'Y',
135
- shipping_length: sanitize(row[74]),
136
- shipping_width: sanitize(row[75]),
137
- shipping_height: sanitize(row[76]),
138
- }
139
- end
140
-
141
- ftp.close
142
- end
143
-
144
- items
145
- end
146
-
147
- def process_as_chunks(size, &block)
148
- connect(@options) do |ftp|
149
- chunker = RsrGroup::Chunker.new(size)
150
- temp_csv_file = Tempfile.new
151
-
152
- # Is this a key dealer?
153
- if ftp.nlst.include?(KEYDEALER_DIR)
154
- ftp.chdir(KEYDEALER_DIR)
155
-
156
- # Pull from the FTP and save as a temp file
157
- ftp.getbinaryfile(KEYDEALER_FILENAME, temp_csv_file.path)
158
- else
159
- ftp.chdir(INVENTORY_DIR)
160
-
161
- # Pull from the FTP and save as a temp file
162
- ftp.getbinaryfile(INVENTORY_FILENAME, temp_csv_file.path)
163
- end
164
-
165
- # total_count is the number of lines in the file
166
- chunker.total_count = File.readlines(temp_csv_file).size
167
-
168
- CSV.readlines(temp_csv_file, col_sep: ';', quote_char: "\x00").to_enum.with_index(1).each do |row, current_line|
169
-
170
- if chunker.is_full?
171
- yield(chunker.chunk)
172
-
173
- chunker.reset
174
- elsif chunker.is_complete?
175
- yield(chunker.chunk)
176
-
177
- break
178
- else
179
- chunker.add(process_row(row))
180
- end
181
- end
182
-
183
- temp_csv_file.unlink
184
- ftp.close
185
- end
186
- end
187
-
188
- def map_prices
189
- rows = []
190
-
191
- connect(@options) do |ftp|
192
- if ftp.nlst.include?(KEYDEALER_DIR)
193
- ftp.chdir(KEYDEALER_DIR)
194
- else
195
- ftp.chdir(INVENTORY_DIR)
196
- end
197
-
198
- ftp.gettextfile(MAP_FILENAME, nil) do |line|
199
- points = line.split(',').map(&:rstrip)
200
- rows << {
201
- stock_number: points[0],
202
- map_price: points[1],
203
- }
204
- end
205
-
206
- ftp.close
207
- end
208
-
209
- rows
210
- end
211
-
212
- def map_prices_as_chunks(size, &block)
213
- connect(@options) do |ftp|
214
- chunker = RsrGroup::Chunker.new(size)
215
- temp_csv_file = Tempfile.new
216
-
217
- # Is this a key dealer?
218
- if ftp.nlst.include?(KEYDEALER_DIR)
219
- ftp.chdir(KEYDEALER_DIR)
220
- else
221
- ftp.chdir(INVENTORY_DIR)
222
- end
223
-
224
- # Pull from the FTP and save as a temp file
225
- ftp.getbinaryfile(MAP_FILENAME, temp_csv_file.path)
226
-
227
- # total_count is hte number of lines in the file
228
- chunker.total_count = File.readlines(temp_csv_file).size
229
-
230
- CSV.readlines(temp_csv_file).each do |row|
231
- if chunker.is_full?
232
- yield(chunker.chunk)
233
-
234
- chunker.reset
235
- elsif chunker.is_complete?
236
- yield(chunker.chunk)
237
-
238
- break
239
- else
240
- chunker.add({
241
- stock_number: row[0].strip,
242
- map_price: row[1]
243
- })
244
- end
245
- end
246
-
247
- temp_csv_file.unlink
248
- ftp.close
249
- end
250
- end
251
-
252
- def quantities
253
- rows = []
254
-
255
- connect(@options) do |ftp|
256
- if ftp.nlst.include?(KEYDEALER_DIR)
257
- ftp.chdir(KEYDEALER_DIR)
258
- else
259
- ftp.chdir(INVENTORY_DIR)
260
- end
261
-
262
- csv = ftp.gettextfile(QTY_FILENAME, nil)
263
-
264
- CSV.parse(csv) do |row|
265
- rows << {
266
- stock_number: row[0].rstrip,
267
- quantity: row[1].to_i,
268
- }
269
- end
270
-
271
- ftp.close
272
- end
273
-
274
- rows
17
+ new(options).all(chunk_size, &block)
275
18
  end
276
19
 
277
- def quantities_as_chunks(size, &block)
20
+ def all(chunk_size, &block)
278
21
  connect(@options) do |ftp|
279
- chunker = RsrGroup::Chunker.new(size)
280
- temp_csv_file = Tempfile.new
22
+ chunker = RsrGroup::Chunker.new(chunk_size)
23
+ csv_tempfile = Tempfile.new
281
24
 
282
25
  # Is this a key dealer?
283
26
  if ftp.nlst.include?(KEYDEALER_DIR)
@@ -287,12 +30,12 @@ module RsrGroup
287
30
  end
288
31
 
289
32
  # Pull from the FTP and save as a temp file
290
- ftp.getbinaryfile(QTY_FILENAME, temp_csv_file.path)
33
+ ftp.getbinaryfile(QTY_FILENAME, csv_tempfile.path)
291
34
 
292
35
  # total_count is hte number of lines in the file
293
- chunker.total_count = File.readlines(temp_csv_file).size
36
+ chunker.total_count = File.readlines(csv_tempfile).size
294
37
 
295
- CSV.readlines(temp_csv_file).each do |row|
38
+ CSV.readlines(csv_tempfile).each do |row|
296
39
  if chunker.is_full?
297
40
  yield(chunker.chunk)
298
41
 
@@ -303,106 +46,16 @@ module RsrGroup
303
46
  break
304
47
  else
305
48
  chunker.add({
306
- stock_number: row[0].rstrip,
307
- quantity: row[1].to_i
49
+ item_identifier: row[0].rstrip,
50
+ quantity: row[1].to_i
308
51
  })
309
52
  end
310
53
  end
311
54
 
312
- temp_csv_file.unlink
55
+ csv_tempfile.unlink
313
56
  ftp.close
314
57
  end
315
58
  end
316
59
 
317
-
318
- private
319
-
320
- def sanitize(data)
321
- return data unless data.is_a?(String)
322
- data.strip
323
- end
324
-
325
- def process_row(row)
326
- {
327
- stock_number: sanitize(row[0]),
328
- upc: sanitize(row[1]),
329
- description: sanitize(row[2]),
330
- department: row[3].nil? ? row[3] : RsrGroup::Department.new(row[3]),
331
- manufacturer_id: sanitize(row[4]),
332
- retail_price: sanitize(row[5]),
333
- regular_price: sanitize(row[6]),
334
- weight: sanitize(row[7]),
335
- quantity: (Integer(sanitize(row[8])) rescue 0),
336
- model: sanitize(row[9]),
337
- manufacturer_name: sanitize(row[10]),
338
- manufacturer_part_number: sanitize(row[11]),
339
- allocated_closeout_deleted: sanitize(row[12]),
340
- description_full: sanitize(row[13]),
341
- image_name: sanitize(row[14]),
342
- restricted_states: {
343
- AK: row[15] == 'Y',
344
- AL: row[16] == 'Y',
345
- AR: row[17] == 'Y',
346
- AZ: row[18] == 'Y',
347
- CA: row[19] == 'Y',
348
- CO: row[20] == 'Y',
349
- CT: row[21] == 'Y',
350
- DC: row[22] == 'Y',
351
- DE: row[23] == 'Y',
352
- FL: row[24] == 'Y',
353
- GA: row[25] == 'Y',
354
- HI: row[26] == 'Y',
355
- IA: row[27] == 'Y',
356
- ID: row[28] == 'Y',
357
- IL: row[29] == 'Y',
358
- IN: row[30] == 'Y',
359
- KS: row[31] == 'Y',
360
- KY: row[32] == 'Y',
361
- LA: row[33] == 'Y',
362
- MA: row[36] == 'Y',
363
- MD: row[37] == 'Y',
364
- ME: row[38] == 'Y',
365
- MI: row[39] == 'Y',
366
- MN: row[40] == 'Y',
367
- MO: row[41] == 'Y',
368
- MS: row[42] == 'Y',
369
- MT: row[43] == 'Y',
370
- NC: row[44] == 'Y',
371
- ND: row[45] == 'Y',
372
- NE: row[46] == 'Y',
373
- NH: row[47] == 'Y',
374
- NJ: row[48] == 'Y',
375
- NM: row[49] == 'Y',
376
- NV: row[50] == 'Y',
377
- NY: row[51] == 'Y',
378
- OH: row[52] == 'Y',
379
- OK: row[53] == 'Y',
380
- OR: row[54] == 'Y',
381
- PA: row[55] == 'Y',
382
- RI: row[56] == 'Y',
383
- SC: row[57] == 'Y',
384
- SD: row[58] == 'Y',
385
- TN: row[59] == 'Y',
386
- TX: row[60] == 'Y',
387
- UT: row[61] == 'Y',
388
- VA: row[62] == 'Y',
389
- VT: row[63] == 'Y',
390
- WA: row[64] == 'Y',
391
- WI: row[65] == 'Y',
392
- WV: row[66] == 'Y',
393
- WY: row[67] == 'Y',
394
- },
395
- ground_shipping_only: row[68] == 'Y',
396
- adult_signature_required: row[69] == 'Y',
397
- blocked_from_drop_ship: row[70] == 'Y',
398
- date_entered: row[71].nil? ? row[71] : Date.strptime(row[71], '%Y%m%d'),
399
- retail_map: sanitize(row[72]),
400
- image_disclaimer: row[73] == 'Y',
401
- shipping_length: sanitize(row[74]),
402
- shipping_width: sanitize(row[75]),
403
- shipping_height: sanitize(row[76]),
404
- }
405
- end
406
-
407
60
  end
408
61
  end
@@ -7,17 +7,6 @@ module RsrGroup
7
7
  # * Call {#submit!} to send the order
8
8
  class Order < Base
9
9
 
10
- class ResponseStruct < Struct.new(:success, :message, :data)
11
-
12
- # Simple response object to pass along success/falure/messages of any process
13
- # Usage:
14
- # response = ResponseStruct.new(true)
15
- # response = ResponseStruct.new(false, "You did the wrong thing")
16
- # response = ResponseStruct.new(true, nil, { result: 200 })
17
-
18
- alias success? success
19
- end
20
-
21
10
  # @param [Hash] options
22
11
  # @option options [String] :merchant_number *required*
23
12
  # @option options [Integer] :sequence_number *required*
@@ -98,16 +87,12 @@ module RsrGroup
98
87
  io = StringIO.new(to_txt)
99
88
  begin
100
89
  ftp.storlines("STOR " + filename, io)
101
- success = ftp.nlst.include?(filename)
102
- @response = ResponseStruct.new(success, nil, modified: ftp.mtime(filename), size: ftp.size(filename))
103
90
  ensure
104
91
  io.close
105
92
  end
106
93
  ftp.close
107
94
  end
108
- @response || ResponseStruct.new(false)
109
- rescue Net::FTPPermError => e
110
- return ResponseStruct.new(false, e.message.chomp)
95
+ true
111
96
  end
112
97
 
113
98
  private
@@ -1,3 +1,3 @@
1
1
  module RsrGroup
2
- VERSION = '1.8.0'.freeze
2
+ VERSION = '2.0.1'.freeze
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rsr_group
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.8.0
4
+ version: 2.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Dale Campbell
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2018-04-23 00:00:00.000000000 Z
11
+ date: 2017-10-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: smarter_csv
@@ -101,6 +101,7 @@ files:
101
101
  - config.rb.example
102
102
  - lib/rsr_group.rb
103
103
  - lib/rsr_group/base.rb
104
+ - lib/rsr_group/catalog.rb
104
105
  - lib/rsr_group/chunker.rb
105
106
  - lib/rsr_group/constants.rb
106
107
  - lib/rsr_group/data_row.rb
@@ -134,7 +135,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
134
135
  version: '0'
135
136
  requirements: []
136
137
  rubyforge_project:
137
- rubygems_version: 2.6.12
138
+ rubygems_version: 2.5.1
138
139
  signing_key:
139
140
  specification_version: 4
140
141
  summary: RSR Group Ruby library