sushi_counter 0.0.1 → 0.1.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 (3) hide show
  1. checksums.yaml +4 -4
  2. data/sushi_counter.rb +85 -63
  3. metadata +18 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: c887dfdb40f6bcc9f4365e6db790c79c187d7d62
4
- data.tar.gz: 9887a751bf58b979c0857facff0a2522c54fb296
3
+ metadata.gz: 0d6e5e173e88c45200a3f4966060ce1153f93d6a
4
+ data.tar.gz: 30817939966490cbcd1667cdeed0778b722cb555
5
5
  SHA512:
6
- metadata.gz: e84b56c117927189ed262586818a051110bc5733c671100a4c9b713a6cd1f519386743f50591dfa050408ca1d64d7bc0498a2f0dca208ea91e659f65b5792c5a
7
- data.tar.gz: b5f1fa348245c03d2ba85dfdfb071162d14110acfbd8f54eced1ba2dc733d4fb249f4859964a2a22a365db06cc3b2ed73cbddbf4f14917f76a18938c4c6492f2
6
+ metadata.gz: 5c7fa75cf5156ffb4b97f6cf065cea398874007eecd57ca20519dc584707ceaf7a128a48f01af5626465acdc4a495c7573c12ed27994a3428eadb9875eca4996
7
+ data.tar.gz: 6f0366b9ea9c058a58a5e5ddccf54ac1528b8778ef0b5914fc39ceb04dd0ce7a8ab98e844103d2aa33ee41e498c01d7b8cced2b7c4c35311380de7f6767f6886
data/sushi_counter.rb CHANGED
@@ -4,6 +4,7 @@ require 'Savon'
4
4
  require 'csv'
5
5
  require 'nokogiri'
6
6
  require 'date'
7
+ require 'rainbow'
7
8
 
8
9
  #Creating options, flags and switches for CLI app.
9
10
  options = {}
@@ -15,15 +16,16 @@ option_parser = OptionParser.new do |opts|
15
16
  Usage: #{executable_name} [options] output_file.csv
16
17
 
17
18
  "
18
- opts.on("-u [URL]",
19
- "URL is the url to the WSDL file specified by the vendor. It will always end in ?wsdl. If you are passing an endpoint, leave this blank."
20
- ) do |url|
21
- options[:url] = url
19
+ #All URLs seem to work if endpoint is combined with default WSDL URL. Leave commented for now.
20
+ #opts.on("-u [URL]",
21
+ #{}"URL is the url to the WSDL file specified by the vendor. It will always end in ?wsdl. If you are passing an endpoint, leave this blank."
22
+ #) do |url|
23
+ # options[:url] = url
22
24
  #Check if a WSDL was passed, if not, put in generic WSDL.
23
- if options[:url].nil?
24
- options[:url] = "http://www.niso.org/schemas/sushi/counter_sushi4_0.wsdl"
25
- end
26
- end
25
+ # if options[:url].nil?
26
+ # options[:url] = "http://www.niso.org/schemas/sushi/counter_sushi4_0.wsdl"
27
+ # end
28
+ # end
27
29
  opts.on("-E ENDPOINT",
28
30
  "Endpoint is the url to the service specified by the vendor. It will end with anything but ?wsdl."
29
31
  ) do |endpoint|
@@ -41,26 +43,25 @@ option_parser = OptionParser.new do |opts|
41
43
  end
42
44
  opts.on("-s REPORT_START",
43
45
  "Start date of report in YYYY-MM-DD format.",
44
- #RegEx to validate date not working. Need to fix.
45
- #/^\d{4}\-(0?[1-9]|1[012])\-(0?[1-9]|[12][0-9]|3[01])$/
46
+ /^\d{4}-\d{2}-\d{2}$/
46
47
  ) do |report_start|
47
48
  options[:report_start] = report_start
48
49
  end
49
50
  opts.on("-e REPORT_END",
50
51
  "End date of report in YYYY-MM-DD format. DD must be the end of the month (e.g. 31)",
51
- #RegEx to validate date not working. Need to fix
52
- #/^\d{4}\-(0?[1-9]|1[012])\-(0?[1-9]|[12][0-9]|3[01])$/
52
+ /^\d{4}-\d{2}-\d{2}$/
53
53
  ) do |report_end|
54
54
  options[:report_end] = report_end
55
55
  end
56
- opts.on("-t TYPE",
57
- "Specify which type of COUNTER report you want. If left empty, the default is JR1."
58
- ) do |type|
59
- options[:type] = type
60
- if options[:type].nil?
61
- options[:type] = "JR1"
62
- end
63
- end
56
+ #Can only fetch one report type at the moment. Add back in later.
57
+ #opts.on("-t [TYPE]",
58
+ #{}"Specify which type of COUNTER report you want. If left empty, the default is JR1."
59
+ #) do |type|
60
+ # options[:type] = type
61
+ # if options[:type].nil?
62
+ # options[:type] = "JR1"
63
+ # end
64
+ # end
64
65
  opts.on("-p [PASSWORD]",
65
66
  "Specify your requestor email/password if required by the vendor."
66
67
  ) do |password|
@@ -69,43 +70,48 @@ option_parser = OptionParser.new do |opts|
69
70
  options[:password] = "Blank"
70
71
  end
71
72
  end
72
- #Add switch for logging on/off?
73
+
74
+ #Add switch for logging on/off?
75
+ options[:log] = false
76
+ opts.on("-l","--log") do options[:log] = true
77
+ end
78
+
73
79
  end
74
80
  begin
75
81
  option_parser.parse!
76
82
  if ARGV.empty?
77
- puts "error: you must supply an output_file in format 'output_file.csv'"
83
+ puts Rainbow("error: you must supply an output_file in format 'output_file.csv'").bright.red
78
84
  puts
79
85
  puts option_parser.help
80
- exit 1
86
+ exit 2
81
87
  else
82
88
  output_file = ARGV[0]
83
89
  end
84
- rescue OptionParser::InvalidArgument => ex
85
- STDERR.puts ex.message
86
- STDERR.puts option_parser
87
- end
88
90
  if ARGV.include? 'DEBUG'
89
91
  puts "The parameters you are passing to each option are:"
90
- puts "url: #{options[:url]}"
92
+ #puts "url: #{options[:url]}"
91
93
  puts "endpoint: #{options[:endpoint]}"
92
94
  puts "requestor: #{options[:requestor]}"
93
95
  puts "customer: #{options[:customer]}"
94
96
  puts "report_start: #{options[:report_start]}"
95
97
  puts "report_end: #{options[:report_end]}"
98
+ #puts "type: #{options[:type]}"
96
99
  puts "password: #{options[:password]}"
100
+ puts "log level: #{options[:log]}"
101
+ end
102
+ rescue OptionParser::InvalidArgument => ex
103
+ STDERR.puts Rainbow("#{ex.message}").bright.red
104
+ STDERR.puts option_parser
105
+ exit 3
97
106
  end
98
-
99
107
 
100
108
  define_method :sushi_call do
101
109
  #Set up client for connection
102
110
  client = Savon.client(
103
- #This needs to be passed as a variable. Store all WSDLs as an array and allow
104
- #users to select from array?
105
- wsdl: "#{options[:url]}",
111
+ #Possible to set up options below with YAML or CSV import?
112
+ wsdl: "http://www.niso.org/schemas/sushi/counter_sushi4_0.wsdl",
106
113
  endpoint: "#{options[:endpoint]}",
107
- #I think these can stay static, need to validate against a different WSDL. May
108
- #need to add additional namespaces?
114
+ #Keep namespaces static
109
115
  namespaces:{
110
116
  "xmlns:tns" => "SushiService",
111
117
  "xmlns:sc" => "http://www.niso.org/schemas/sushi/counter",
@@ -115,17 +121,15 @@ define_method :sushi_call do
115
121
  "xmlns:soap" => "http://schemas.xmlsoap.org/wsdl/soap",
116
122
  "xmlns:soap12" => "http://schemas.xmlsoap.org/wsdl/soap12/"
117
123
  },
118
- #Probably keep this static so users don't have to mess with their keys. But need to check
119
- #if all keys are the same in each WSDL.
124
+ #Keep keys static
120
125
  convert_request_keys_to: :none,
121
- #Logging info. Allow users to set this as a flag to output more/less info. Default should
122
- #be minimal.
123
- log: true,
126
+ #Logging info. Always keep to debug. Default is false, unless specified by user
127
+ log: options[:log],
124
128
  log_level: :debug,
125
129
  #Allow users to control if they desire - outputs XML to terminal. Default should be FALSE.
126
130
  #Pretty Print is dependent on logging being on
127
131
  pretty_print_xml: true,
128
- #Mandatory? I think so. Keep static.
132
+ #Keep static.
129
133
  env_namespace: :soapenv
130
134
  )
131
135
  #Send out call for data, passing all parameters for login/data
@@ -152,10 +156,12 @@ define_method :sushi_call do
152
156
  :attributes! => {
153
157
  "sus:ReportDefinition" => {
154
158
  "Release" => "4",
155
- "Name" => "#{options[:type]}"
159
+ "Name" => "JR1"
156
160
  },
157
161
  },
158
162
  } )
163
+ puts "Fetching report..."
164
+ begin
159
165
 
160
166
  xml = response.doc
161
167
  #Need to replace below xml file with a dynamically generated name based on vendor/year.
@@ -173,8 +179,6 @@ define_method :sushi_call do
173
179
 
174
180
  month_array = []
175
181
  #Math to get number of months and print out to headers
176
- r_start = options[:report_start]
177
- r_end = options[:report_end]
178
182
  define_method(:months_math) do |date1, date2|
179
183
  m = (date2.year * 12 + date2.month) - (date1.year * 12 + date1.month) + 1
180
184
  m.times do |n|
@@ -182,20 +186,24 @@ define_method :sushi_call do
182
186
  month_array << iterator.to_s
183
187
  end
184
188
  end
189
+
185
190
  #Turn report_start and report_end into something readable.
191
+ r_start = options[:report_start]
192
+ r_end = options[:report_end]
186
193
  date_start = Date.parse(r_start)
187
194
  date_end = Date.parse(r_end)
195
+ #Call months_math method
188
196
  months_var = months_math(date_start, date_end)
189
197
  count_var = months_var - 1
190
198
 
191
- #Basic info about report.
199
+ #Grabbing basic info about report.
192
200
  doc_requestor = noko_doc.xpath('//Requestor/ID').text
193
201
  doc_customer_ref = noko_doc.xpath('//CustomerReference/ID').text
194
202
  doc_release = noko_doc.xpath('//ReportDefinition').attr('Release').text
195
203
  doc_version = noko_doc.xpath('//ReportDefinition').attr('Name').text
196
204
 
197
205
 
198
- #Setting empty arrays and variables to manage scope
206
+ #Setting empty arrays, hashes and variables to manage scope
199
207
  pdf_stats = []
200
208
  pdf_holder = []
201
209
  html_stats = []
@@ -213,7 +221,12 @@ define_method :sushi_call do
213
221
  html_iterator = nil
214
222
  iterator = nil
215
223
  total_pdf = nil
224
+ total_html = nil
225
+ total_all = nil
216
226
  i = 0
227
+ platform = nil
228
+ total_integer = nil
229
+ #total_months = []
217
230
 
218
231
 
219
232
  noko_doc.xpath('//ReportItems').each do |item|
@@ -225,9 +238,6 @@ define_method :sushi_call do
225
238
  publisher = item.xpath("./ItemPublisher").text
226
239
  name = item.xpath("./ItemName").text
227
240
 
228
- #Probably don't need the line below
229
- datatype = item.xpath("./ItemDataType").text
230
-
231
241
  #Store all months from XML data into an array
232
242
  month_match = item.xpath("./ItemPerformance/Period").each do |match|
233
243
  matches = match.xpath("./Begin").text
@@ -243,6 +253,7 @@ define_method :sushi_call do
243
253
  count_hash[month.to_sym] = counts
244
254
  end
245
255
 
256
+
246
257
  n = 0
247
258
  m = 0
248
259
 
@@ -253,7 +264,6 @@ define_method :sushi_call do
253
264
  if month_holder.include? month_array[n]
254
265
  month_key = month_array[n]
255
266
  count = count_hash[month_key.to_sym]
256
- #i += 1
257
267
  m += 1
258
268
  total_stats << count
259
269
  if n < count_var
@@ -261,28 +271,27 @@ define_method :sushi_call do
261
271
  else n = 0
262
272
  end
263
273
  else
264
- fallback_count = "test"
274
+ fallback_count = "0"
265
275
  total_stats << fallback_count
266
276
  if n < count_var
267
277
  n += 1
268
278
  else n = 0
269
279
  end
270
280
  end
271
- stats = item.xpath("./ItemPerformance").each do |month|
272
- count_html = month.xpath("./Instance[MetricType = 'ft_html']/Count").text
273
- count_pdf = month.xpath("./Instance[MetricType = 'ft_pdf']/Count").text
274
- pdf_stats << count_pdf
275
- html_stats << count_html
281
+ end
276
282
 
277
- #Add total columns here. Need more (html, all, each month, etc...)
278
- total_pdf = pdf_stats.map(&:to_i).reduce(:+)
279
- end
283
+ stats = item.xpath("./ItemPerformance").each do |month|
284
+ count_html = month.xpath("./Instance[MetricType = 'ft_html']/Count").text
285
+ count_pdf = month.xpath("./Instance[MetricType = 'ft_pdf']/Count").text
286
+ pdf_stats << count_pdf
287
+ html_stats << count_html
280
288
  end
281
289
 
282
290
  #Make code below DRYer
283
291
  #Refine code below? Currently working, but could probably be DRYer
284
292
  total_stats.each_slice(months_var).each do |slice|
285
293
  iterator = slice.join(",")
294
+ total_integer = slice.map(&:to_i).inject(0, :+)
286
295
  end
287
296
  #Could probably just add up html_stats array and output in CSV row below.
288
297
  html_stats.each_slice(months_var).each do |slice|
@@ -302,6 +311,11 @@ define_method :sushi_call do
302
311
  report_data << [name, publisher, platform, doi, value, print_issn, online_issn, total_iterator, html_iterator, pdf_iterator, iterator]
303
312
  end
304
313
 
314
+ #Add total columns here. Need more (html, all, each month, etc...)
315
+ total_pdf = pdf_stats.map(&:to_i).reduce(:+)
316
+ total_html = html_stats.map(&:to_i).reduce(:+)
317
+ total_all = total_html + total_pdf
318
+
305
319
  ##Output Nokogiri Doc into csv
306
320
  CSV.open(output_file, 'wb') do |row|
307
321
  row << ["#{doc_version}", "Release: #{doc_release}"]
@@ -311,17 +325,25 @@ define_method :sushi_call do
311
325
  row << ["Date run:"]
312
326
  row << ["#{Time.now.strftime("%d/%m/%Y")}"]
313
327
 
314
- #This row needs to include month/year for each month. So need to get number
315
- # of months from above (slice parentheses value) and year from input. Also, commas aren't automatically spacing out to new column when opened in CSV.
328
+ #Prints all headers
316
329
  row << ["Journal", "Publisher", "Platform", "Journal DOI", "Proprietary Identifier", "Print ISSN", "Online ISSN", "Reporting Period Total", "Reporting Period HTML", "Reporting Period PDF", month_array]
317
- row << [total_pdf]
318
- #Add line that totals all data?
319
- # row <<
330
+ #Prints totals of all data - need to add more totals.
331
+ row << ["Total for all Journals", "", platform, "","","","", total_all, total_html, total_pdf, total_integer]
320
332
 
321
333
  #Code below iterates through array, printing each item to a row
322
334
  report_data.each do |data|
323
335
  row << data
324
336
  end
325
337
  end
338
+ rescue
339
+ puts Rainbow("There was an error running the script. Double check the values you are passing to the script and try adding '--log' to your command
340
+ to see what went wrong.").bright.red
341
+ else
342
+ #Rewrite XML filename to something more useful (e.g. vendor name)?
343
+ #Add statements to check if files actually created.
344
+ puts "The XML file is in the" + Rainbow(" 'raw_xml/'").green.bright + " folder and the filename is" + Rainbow(" '#{options[:customer]}-#{Time.now.strftime("%Y%m%d")}.xml'").green.bright
345
+ puts "Your COUNTER report is in the file" + Rainbow(" '#{ARGV[0]}'").green.bright
346
+ end
326
347
  end
348
+
327
349
  sushi_call()
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sushi_counter
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1
4
+ version: 0.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Max King
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-10-19 00:00:00.000000000 Z
11
+ date: 2017-10-30 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: savon
@@ -38,6 +38,20 @@ dependencies:
38
38
  - - ">="
39
39
  - !ruby/object:Gem::Version
40
40
  version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rainbow
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
41
55
  - !ruby/object:Gem::Dependency
42
56
  name: aruba
43
57
  requirement: !ruby/object:Gem::Requirement
@@ -54,7 +68,8 @@ dependencies:
54
68
  version: 0.5.3
55
69
  description: |-
56
70
  Sushi fetches the raw XML from a number of vendors, then
57
- converts that data into a human readable CSV
71
+ converts that data into a human readable CSV. For more info please visit
72
+ https://github.com/maxdavidking/CLIapp
58
73
  email:
59
74
  - maxdavidking at gmail.com
60
75
  executables: