csv_pirate 3.4.4 → 4.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG CHANGED
@@ -1,3 +1,13 @@
1
+ Version 4.0.1 2010-01-15
2
+ - Improving import / export
3
+ - Updating Readme to reflect 4.0.0 API
4
+
5
+ Version 4.0.0 2010-01-14 (never released)
6
+ - CSV Imports from old CsvPirate Dumps
7
+ - Lots of refactoring
8
+ - Lots of bug reduction
9
+ - added Rspec tests!
10
+
1
11
  Version 3.4.4 2009-11-10
2
12
  - Fixed installation instructions to refer to gemcutter, and removed github as gemhost
3
13
 
data/README.rdoc CHANGED
@@ -2,9 +2,11 @@
2
2
 
3
3
  Easily create CSVs of any data that can be derived from your models.
4
4
 
5
- CsvPirate is the easy way to create a CSV of essentially anything in Rails, in full pirate regalia.
5
+ CsvPirate is the easy way to create a CSV of essentially anything in Ruby, in full pirate regalia.
6
6
  It works better if you are wearing a tricorne!
7
7
 
8
+ Everything in the source that depended on Rails extensions of Ruby classes has been refactored to work in pure Ruby!
9
+
8
10
  My goal is to have it do EVERYTHING it possibly can for me, since almost every project I do needs CSV exports.
9
11
 
10
12
  CsvPirate only works for commissions of swag OR grub!
@@ -33,9 +35,9 @@ Initialize method (a.k.a new()) takes a hash of parameters:
33
35
  # :bury_treasure should we store the csv data as it is collected in an array in Ruby form for later use (true), or just write the CSV (false)?
34
36
  # :blackjack Specify how you want your CSV header
35
37
  # {:join => '-'} joins the method names called to get hte data for that column with '_' underscores.
36
- # {:humanize =>'-'} first joins as above, then humanizes the string
38
+ # {:humanize =>'-'} first joins as above, then humanizes the string (this is the default)
37
39
  # {:array => ['col1',col2','col3'] Uses the column names provided. If the array's length is less than the booty array's length it reverts to :humanize =>'_'
38
- # check the source to see if there anything else hiding in there!
40
+ # check the source to see if there anything else hiding in there! There are a few new options in the 4.0.0 release, which are as yet undocumented.
39
41
 
40
42
  The create method has the same parameters, and actually creates the CSV.
41
43
 
@@ -110,6 +112,8 @@ What's the simplest thing that will work?
110
112
 
111
113
  == Usage without ActiveRecord
112
114
 
115
+ [ See Spec Tests for more Examples! ]
116
+
113
117
  Since the defaults assume an active record class you need to override some of them:
114
118
 
115
119
  class Star
@@ -199,7 +203,7 @@ Assuming a Make (as in manufacturers of automobiles) model like this:
199
203
  :bury_treasure => true # Boolean: Should the array of objects in :swag be stored in the CsvPirate object for later inspection?
200
204
  :blackjack => {:humanize => '-'} # Hash: Specify how you want your CSV header
201
205
  # {:join => '-'} joins the method names called to get hte data for that column with '_' underscores.
202
- # {:humanize => '-'} first joins as above, then humanizes the string
206
+ # {:humanize => '-'} first joins as above, then humanizes the string (this is the default)
203
207
  # {:array => ['col1',col2','col3'] Uses the column names provided in the array. If the array provided is too short defaults to :humanize =>'_'
204
208
 
205
209
  # A customized version to create a tab delimited file for this class might look like this:
@@ -324,13 +328,20 @@ You have the same Make class as above, and you have a MakeController:
324
328
  class MakeController < ApplicationController
325
329
  def download_csv
326
330
  csv_pirate = Make.blindfold
327
- send_data csv_pirate.maroon,
328
- :type => 'text/csv; charset=iso-8859-1; header=present',
329
- :disposition => "attachment; filename=#{csv_pirate.nocturnal}"
331
+
332
+ # maroon saves the read to the file system, by using the text of the csv stored in the CsvPirate object.
333
+ send_data csv_pirate.maroon, ...
334
+ :type => 'text/csv; charset=iso-8859-1; header=present',
335
+ :disposition => "attachment; filename=#{csv_pirate.nocturnal}"
336
+
337
+ # However if CSVs are created using multiple CsvPirate objects that all append to a single file,
338
+ # we need to read the final product from the fs.
339
+ #send_file csv_pirate.brigantine,
340
+ # :type => 'text/csv; charset=utf-8; header=present',
341
+ # :disposition => "attachment; filename=#{csv_pirate.nocturnal}"
330
342
  end
331
343
  end
332
344
 
333
-
334
345
  == Advanced Example with Nested Methods
335
346
 
336
347
  You have a VehicleModel class and the same Make class as up above:
@@ -399,6 +410,14 @@ This allows you to modify the csv_pirate object before creating the csv like thi
399
410
  csv_pirate.booty -= [:id, :name]
400
411
  csv_pirate.hoist_mainstay()
401
412
 
413
+ == Tests
414
+
415
+ The tests are run with rspec. The test suite is expanding. Currently there is ample coverage of basic functionality.
416
+
417
+ To run tests cd to where ever you have csv_pirate installed, and do:
418
+
419
+ rake spec
420
+
402
421
  == BUGS (Not mine, Micrsoft's)
403
422
 
404
423
  Microsoft Office (Excel) "SYLK Invalid Format" Error will occur if the string "ID" (without quotes)
data/Rakefile CHANGED
@@ -4,8 +4,8 @@ begin
4
4
  require 'jeweler'
5
5
  Jeweler::Tasks.new do |gemspec|
6
6
  gemspec.name = "csv_pirate"
7
- gemspec.summary = "Easily create CSVs of any data that can be derived from your models (using pirates!)."
8
- gemspec.description = %q{CsvPirate is the easy way to create a CSV of essentially anything in Rails, in full pirate regalia.
7
+ gemspec.summary = "Easily create CSVs of any data that can be derived from instance methods on your classes."
8
+ gemspec.description = %q{CsvPirate is the easy way to create a CSV of essentially anything in Ruby, in full pirate regalia.
9
9
  It works better if you are wearing a tricorne!}
10
10
  gemspec.email = "peter.boling@gmail.com"
11
11
  gemspec.homepage = "http://github.com/pboling/csv_pirate"
@@ -18,6 +18,12 @@ It works better if you are wearing a tricorne!}
18
18
  "install.rb",
19
19
  "lib/csv_pirate.rb",
20
20
  "lib/ninth_bit/pirate_ship.rb",
21
+ "spec/csv_pirate_spec.rb",
22
+ "spec/pirate_ship_spec.rb",
23
+ "spec/spec.opts",
24
+ "spec/spec_helper.rb",
25
+ "spec/spec_helpers/glowing_gas_ball.rb",
26
+ "spec/spec_helpers/star.rb",
21
27
  "Rakefile",
22
28
  "LICENSE",
23
29
  "CHANGELOG",
data/VERSION.yml CHANGED
@@ -1,5 +1,5 @@
1
1
  ---
2
- :minor: 4
3
- :patch: 4
4
- :major: 3
2
+ :patch: 1
3
+ :major: 4
4
+ :minor: 0
5
5
  :build:
data/csv_pirate.gemspec CHANGED
@@ -5,12 +5,12 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{csv_pirate}
8
- s.version = "3.4.4"
8
+ s.version = "4.0.1"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Peter Boling"]
12
- s.date = %q{2009-11-10}
13
- s.description = %q{CsvPirate is the easy way to create a CSV of essentially anything in Rails, in full pirate regalia.
12
+ s.date = %q{2010-01-15}
13
+ s.description = %q{CsvPirate is the easy way to create a CSV of essentially anything in Ruby, in full pirate regalia.
14
14
  It works better if you are wearing a tricorne!}
15
15
  s.email = %q{peter.boling@gmail.com}
16
16
  s.extra_rdoc_files = [
@@ -28,16 +28,25 @@ It works better if you are wearing a tricorne!}
28
28
  "install.rb",
29
29
  "lib/csv_pirate.rb",
30
30
  "lib/ninth_bit/pirate_ship.rb",
31
- "rails/init.rb"
31
+ "rails/init.rb",
32
+ "spec/csv_pirate_spec.rb",
33
+ "spec/pirate_ship_spec.rb",
34
+ "spec/spec.opts",
35
+ "spec/spec_helper.rb",
36
+ "spec/spec_helpers/glowing_gas_ball.rb",
37
+ "spec/spec_helpers/star.rb"
32
38
  ]
33
39
  s.homepage = %q{http://github.com/pboling/csv_pirate}
34
40
  s.rdoc_options = ["--charset=UTF-8"]
35
41
  s.require_paths = ["lib"]
36
42
  s.rubygems_version = %q{1.3.5}
37
- s.summary = %q{Easily create CSVs of any data that can be derived from your models (using pirates!).}
43
+ s.summary = %q{Easily create CSVs of any data that can be derived from instance methods on your classes.}
38
44
  s.test_files = [
39
45
  "spec/csv_pirate_spec.rb",
40
- "spec/spec_helper.rb"
46
+ "spec/pirate_ship_spec.rb",
47
+ "spec/spec_helper.rb",
48
+ "spec/spec_helpers/glowing_gas_ball.rb",
49
+ "spec/spec_helpers/star.rb"
41
50
  ]
42
51
 
43
52
  if s.respond_to? :specification_version then
data/init.rb CHANGED
@@ -1,9 +1 @@
1
- require 'csv_pirate'
2
- require 'ninth_bit/pirate_ship'
3
-
4
- # If you are using this on a vanilla Ruby class (no rails or active record) then extend your class like this:
5
- # MyClass.send(:extend, NinthBit::PirateShip::ActMethods) if defined?(MyClass)
6
- # Alternatively you can do this inside your class definition:
7
- # class MyClass
8
- # extend NinthBit::PirateShip::ActMethods
9
- # end
1
+ require 'rails/init'
data/lib/csv_pirate.rb CHANGED
@@ -7,12 +7,12 @@
7
7
  #Version: 1.0
8
8
  #Project owners:
9
9
  # peter.boling (The Cap'n)
10
- require 'faster_csv' unless defined?(FasterCSV)
11
10
 
12
11
  class CsvPirate
13
12
 
14
13
  BOOKIE = [:counter, :timestamp, :none]
15
14
  MOP_HEADS = [:clean, :dirty]
15
+ BRIGANTINE = [:first, :last]
16
16
 
17
17
  attr_accessor :waggoner # First part of filename
18
18
  attr_accessor :chart # directory, default is (['log','csv'])
@@ -52,7 +52,11 @@ class CsvPirate
52
52
  # {:humanize => '-'} first joins as above, then humanizes the string
53
53
  # {:array => ['col1',col2','col3'] Uses the column names provided in the array. If the array provided is too short defaults to :humanize =>'_'
54
54
 
55
- cattr_accessor :parlay # verbosity on a scale of 0 - 3 (0=:none, 1=:error, 2=:info, 3=:debug, 0 being no screen output, 1 is default
55
+ attr_accessor :brigantine # the complete file path
56
+ attr_accessor :pinnacle # the complete file path
57
+ class << self
58
+ attr_accessor :parlay # verbosity on a scale of 0 - 3 (0=:none, 1=:error, 2=:info, 3=:debug, 0 being no screen output, 1 is default
59
+ end
56
60
 
57
61
  # CsvPirate only works for commissions of swag OR grub!
58
62
  # :swag the ARrr collection of swag to work on (optional)
@@ -81,15 +85,15 @@ class CsvPirate
81
85
  # See README for examples
82
86
 
83
87
  def initialize(*args)
84
- raise ArgumentError, "must provide required options" if args.blank?
88
+ raise ArgumentError, "must provide required options" if args.nil?
85
89
 
86
90
  @swag = args.first[:swag]
87
91
  @grub = args.first[:grub]
88
92
 
89
93
  # if they provide both
90
- raise ArgumentError, "must provide either :swag or :grub, not both" if !self.swag.blank? && !self.grub.blank?
94
+ raise ArgumentError, "must provide either :swag or :grub, not both" if !self.swag.nil? && !self.grub.nil?
91
95
  # if they provide neither
92
- raise ArgumentError, "must provide either :swag or :grub" if self.swag.blank? && self.grub.blank?
96
+ raise ArgumentError, "must provide either :swag or :grub" if self.swag.nil? && self.grub.nil?
93
97
 
94
98
  @swab = args.first[:swab] || :counter
95
99
  raise ArgumentError, ":swab is #{self.swab.inspect}, but must be one of #{CsvPirate::BOOKIE.inspect}" unless CsvPirate::BOOKIE.include?(self.swab)
@@ -103,16 +107,17 @@ class CsvPirate
103
107
  @waggoner = args.first[:waggoner] || "#{self.grub || self.swag}"
104
108
  raise ArgumentError, ":waggoner is #{self.waggoner.inspect}, and must be a string at least one character long" if self.waggoner.nil? || self.waggoner.length < 1
105
109
 
106
- @booty = args.first[:booty] || []
110
+ @booty = args.first[:booty] || [] # would like to use Class#instance_variables for generic classes
107
111
  raise ArgumentError, ":booty is #{self.booty.inspect}, and must be an array of methods to call on a class for CSV data" if self.booty.nil? || !self.booty.is_a?(Array) || self.booty.empty?
108
112
 
109
113
  @chart = args.first[:chart] || ['log','csv']
110
114
  raise ArgumentError, ":chart is #{self.chart.inspect}, and must be an array of directory names, which will become the filepath for the csv file" if self.chart.nil? || !self.chart.is_a?(Array) || self.chart.empty?
111
115
 
112
116
  @aft = args.first[:aft] || '.csv'
113
- @chronometer = args.first[:chronometer] == false ? false : args.first[:chronometer] || Date.today
117
+ @chronometer = args.first[:chronometer] == false ? false : (args.first[:chronometer] || Date.today)
118
+
119
+ @spyglasses = (args.first[:spyglasses] || (self.respond_to?(:all) ? [:all] : nil)) if self.grub
114
120
 
115
- @spyglasses = (args.first[:spyglasses] || [:all]) if self.grub
116
121
  @shrouds = args.first[:shrouds] || ',' # for tsv, tab-delimited, "\t"
117
122
  raise ArgumentError, ":shrouds is #{self.shrouds.inspect}, and must be a string (e.g. ',' or '\t'), which will be used as the delimeter for the csv file" if self.shrouds.nil? || !self.shrouds.is_a?(String)
118
123
 
@@ -121,8 +126,8 @@ class CsvPirate
121
126
  @bury_treasure = args.first[:astrolabe] || false
122
127
  @buried_treasure = []
123
128
 
124
- #Default is different than default for has_csv_pirate because this might gem wants to be clean for use outside rails, and humanize may not always be defined for String class
125
- @blackjack = args.first[:blackjack] || {:join => '_'}
129
+ #does not rely on rails humanize!
130
+ @blackjack = args.first[:blackjack] || {:humanize => '_'}
126
131
 
127
132
  #Make sure the header array is the same length as the booty columns
128
133
  if self.blackjack.keys.first == :array && (self.blackjack.values.first.length != self.booty.length)
@@ -130,7 +135,9 @@ class CsvPirate
130
135
  puts "Warning: :blackjack reset to {:join => '_'} because the length of the :booty is different than the length of the array provided to :blackjack" if CsvPirate.parlance(2)
131
136
  end
132
137
 
133
- # Initialize doesn't write anything to a CSV,
138
+ @pinnacle = self.block_and_tackle
139
+
140
+ # Initialize doesn't write anything to a CSV,
134
141
  # but does create the traverse_board and opens the waggoner for reading / writing
135
142
  self.northwest_passage unless self.astrolabe
136
143
 
@@ -140,10 +147,13 @@ class CsvPirate
140
147
  # Once the traverse_board (dir) exists, then check if the rhumb_lines (file) already exists, and set our rhumb_lines counter
141
148
  @swabbie = self.insult_swabbie
142
149
 
143
- @nocturnal = File.basename(self.poop_deck)
150
+ @brigantine = self.poop_deck(args.first[:brigantine])
151
+
152
+ @nocturnal = File.basename(self.brigantine)
153
+
144
154
 
145
155
  # Then open the rhumb_lines
146
- self.rhumb_lines = File.open(File.expand_path(self.poop_deck),self.astrolabe ? "r" : "a")
156
+ self.rhumb_lines = File.open(File.expand_path(self.brigantine),self.astrolabe ? "r" : "a")
147
157
  end
148
158
 
149
159
  def self.create(*args)
@@ -234,7 +244,7 @@ class CsvPirate
234
244
  def jolly_roger
235
245
  if self.bury_treasure
236
246
  if self.buried_treasure.is_a?(Array)
237
- puts "Found #{self.buried_treasure.length} deniers buried here: '#{self.poop_deck}'" if CsvPirate.parlay && CsvPirate.parlance(1)
247
+ puts "Found #{self.buried_treasure.length} deniers buried here: '#{self.brigantine}'" if CsvPirate.parlay && CsvPirate.parlance(1)
238
248
  puts "You must weigh_anchor to review your plunder!" if CsvPirate.parlay && CsvPirate.parlance(1)
239
249
  else
240
250
  puts "Failed to locate treasure" if CsvPirate.parlay && CsvPirate.parlance(1)
@@ -252,35 +262,6 @@ class CsvPirate
252
262
  end
253
263
  end
254
264
 
255
- # create the header of the CSV (column/method names)
256
- # returns an array of strings for CSV header based on blackjack
257
- def block_and_tackle
258
- self.blackjack.map do |k,v|
259
- case k
260
- #Joining is only relevant when the booty contains a nested hash of method calls as at least one of the booty array elements
261
- #Use the booty (methods) as the column headers
262
- when :join then self.binnacle(v, false)
263
- #Use the humanized booty (methods) as the column headers
264
- when :humanize then self.binnacle(v, true)
265
- when :array then v
266
- end
267
- end.first
268
- end
269
-
270
- #returns an array of strings for CSV header based on booty
271
- def binnacle(join_value, humanize = true)
272
- self.booty.map do |compass|
273
- string = compass.is_a?(Hash) ?
274
- self.run_through(compass, join_value) :
275
- compass.is_a?(String) ?
276
- compass :
277
- compass.is_a?(Symbol) ?
278
- compass.to_s :
279
- compass.to_s
280
- humanize ? string.humanize : string
281
- end
282
- end
283
-
284
265
  #Takes a potentially nested hash element of a booty array and turns it into a string for a column header
285
266
  # hash = {:a => {:b => {:c => {:d => {"e" => "fghi"}}}}}
286
267
  # run_through(hash, '_')
@@ -297,30 +278,102 @@ class CsvPirate
297
278
  end
298
279
 
299
280
  #complete file path
300
- def poop_deck
301
- "#{self.analemma}#{self.swabbie}#{self.aft}"
281
+ def poop_deck(brig)
282
+ if BRIGANTINE.include?(brig)
283
+ self.old_csv_dump(brig)
284
+ elsif brig.is_a?(String)
285
+ "#{self.analemma}#{brig}"
286
+ else
287
+ "#{self.analemma}#{self.swabbie}#{self.aft}"
288
+ end
302
289
  end
303
290
 
304
- # Swabs the poop_deck if the mop is clean. (!)
291
+ # Swabs the poop_deck (of the brigantine) if the mop is clean. (!)
305
292
  def swab_poop_deck
306
- self.rhumb_lines.truncate(0) if self.swab == :none && self.mop == :clean && File.size(self.poop_deck) > 0
293
+ self.rhumb_lines.truncate(0) if self.swab == :none && self.mop == :clean && File.size(self.brigantine) > 0
307
294
  end
308
295
 
309
296
  # Must be done on order to rummage through the loot found by the pirate ship
310
297
  def weigh_anchor
311
- CsvPirate.rinse(self.poop_deck)
298
+ CsvPirate.rinse(self.brigantine)
312
299
  end
313
300
 
314
301
  # Sink your own ship! Or run a block of code on each row of the current CSV
315
302
  def scuttle(&block)
316
303
  return false unless block_given?
317
- CsvPirate.broadside(self.poop_deck) do |careen|
304
+ CsvPirate.broadside(self.brigantine) do |careen|
318
305
  yield careen
319
306
  end
320
307
  end
321
308
 
309
+ def to_memory(exclude_id = true, exclude_timestamps = true)
310
+ return nil unless self.grub
311
+ begin
312
+ example = self.grub.new
313
+ rescue Exception
314
+ puts "cannot instantiate instance of #{self.grub} with #{self.grub}.new. CsvPirate#to_memory works most reliably when #{self.grub}.new works with no arguments." if CsvPirate.parlance(1)
315
+ example = nil
316
+ end
317
+ buccaneers = []
318
+ self.scuttle do |row|
319
+ #puts "#{self.pinnacle.first.inspect} #{row[self.pinnacle.first].inspect}"
320
+ buccaneers << self.grub.new(self.data_hash_from_row(row, exclude_id, exclude_timestamps, example))
321
+ end
322
+ buccaneers
323
+ end
324
+
325
+ def data_hash_from_row(row, exclude_id = true, exclude_timestamps = true, example = nil)
326
+ data_hash = {}
327
+ my_booty = self.booty.reject {|x| x.is_a?(Hash)}
328
+ my_booty = exclude_id ? my_booty.reject {|x| a = x.to_sym; [:id, :ID,:dbid, :DBID, :db_id, :DB_ID].include?(a)} : self.booty
329
+ my_booty = exclude_timestamps ? my_booty.reject {|x| a = x.to_sym; [:created_at, :updated_at, :created_on, :updated_on].include?(a)} : self.booty
330
+ my_booty = my_booty.reject {|x| !example.respond_to?("#{x}=".to_sym)} unless example.nil?
331
+ my_booty.each do |method|
332
+ #puts "#{self.pinnacle[index]}"
333
+ data_hash = data_hash.merge({method => row[self.pinnacle[self.booty.index(method)]]})
334
+ end
335
+ #puts "#{data_hash.inspect}"
336
+ data_hash
337
+ end
338
+
339
+ # Grab an old CSV dump (first or last)
340
+ def old_csv_dump(brig)
341
+ file = Dir.entries(self.traverse_board).reject {|x| x.match(/^\./)}.sort.send(brig)
342
+ "#{self.traverse_board}#{file}"
343
+ end
344
+
322
345
  protected
323
346
 
347
+ # create the header of the CSV (column/method names)
348
+ # returns an array of strings for CSV header based on blackjack
349
+ def block_and_tackle
350
+ self.blackjack.map do |k,v|
351
+ case k
352
+ #Joining is only relevant when the booty contains a nested hash of method calls as at least one of the booty array elements
353
+ #Use the booty (methods) as the column headers
354
+ when :join then self.binnacle(v, false)
355
+ #Use the humanized booty (methods) as the column headers
356
+ when :humanize then self.binnacle(v, true)
357
+ when :array then v
358
+ end
359
+ end.first
360
+ end
361
+
362
+ #returns an array of strings for CSV header based on booty
363
+ def binnacle(join_value, humanize = true)
364
+ self.booty.map do |compass|
365
+ string = compass.is_a?(Hash) ?
366
+ self.run_through(compass, join_value) :
367
+ compass.is_a?(String) ?
368
+ compass :
369
+ compass.is_a?(Symbol) ?
370
+ compass.to_s :
371
+ compass.to_s
372
+ humanize ? string.to_s.gsub(/_id$/, "").gsub(/_/, " ").capitalize : string
373
+ end
374
+ end
375
+
376
+ # The directory path to the csv
324
377
  def traverse_board
325
378
  #If we have rails environment then we use rails root, otherwise self.chart stands on its own as a relative path
326
379
  "#{self.north_pole}#{self.chart.join('/')}/"
@@ -358,18 +411,21 @@ class CsvPirate
358
411
  index = base.rindex('.')
359
412
  tail = index.nil? ? nil : base[index+1,base.length]
360
413
  # Ensure numbers
361
- counter = tail.nil? ? 0 : tail[/\d*/].to_i
414
+ tail.nil? ? 0 : tail[/\d*/].to_i
362
415
  end
363
-
416
+
417
+ # Get all the files in the dir
418
+ def axe
419
+ Dir.glob(self.lantern)
420
+ end
421
+
422
+ # File increment for next CSV to dump
364
423
  def boatswain
365
424
  return self.swabbie unless self.swabbie.nil?
366
- counter = 0
367
- bowspirit = Dir.glob(self.lantern)
368
425
  highval = 0
369
- bowspirit.each do |flotsam|
426
+ self.axe.each do |flotsam|
370
427
  counter = self.filibuster(flotsam)
371
428
  highval = ((highval <=> counter) == 1) ? highval : counter
372
- counter = 0
373
429
  end
374
430
  ".#{highval + 1}"
375
431
  end
@@ -409,7 +465,7 @@ class CsvPirate
409
465
  spoils = spoils.send(east.to_sym)
410
466
  unless spoils.nil?
411
467
  if west.is_a?(Hash)
412
- # Recursive nadness is here!
468
+ # Recursive madness is here!
413
469
  spoils = CsvPirate.marlinespike(spoils, west)
414
470
  else
415
471
  spoils = spoils.send(west.to_sym)
@@ -431,9 +487,7 @@ class CsvPirate
431
487
  # Sink other ships! Or run a block of code on each row of a CSV
432
488
  def self.broadside(galley, &block)
433
489
  return false unless block_given?
434
- count = 1 if report_kills
435
490
  FasterCSV.foreach(galley, {:headers => :first_row, :return_headers => false}) do |gun|
436
- puts "Galleys sunk: #{count+=1}" if CsvPirate.parlance(1)
437
491
  yield gun
438
492
  end
439
493
  end
@@ -11,15 +11,16 @@ module NinthBit
11
11
  options[:chart] ||= ['log','csv']
12
12
  options[:aft] ||= '.csv'
13
13
  options[:gibbet] ||= '.export'
14
- #Needs to be defined at runtime, doesn't make sense here
15
- #options[:chronometer] ||= Date.today
14
+ #Needs to be defined at runtime, doesn't make sense here unless set to false, except to be overridden at runtime
15
+ # Default is nil so that the CsvPirate default will kick-in.
16
+ options[:chronometer] ||= nil
16
17
  options[:waggoner] ||= "#{self}"
17
18
  options[:swag] ||= nil
18
19
  options[:swab] ||= :counter
19
20
  options[:mop] ||= :clean
20
21
  options[:shrouds] ||= ','
21
22
  options[:grub] ||= self if options[:swag].nil?
22
- options[:spyglasses] ||= [:all]
23
+ options[:spyglasses] ||= (self.respond_to?(:all) ? [:all] : nil) if options[:grub]
23
24
  # Have to protect against model definitions pre-migration, since column names will fail if
24
25
  options[:booty] ||= check_booty ? self.column_names : []
25
26
  options[:bury_treasure] ||= true
@@ -27,9 +28,9 @@ module NinthBit
27
28
  options[:parlay] ||= 1
28
29
 
29
30
  # if they provide both
30
- raise ArgumentError, "must provide either :swag or :grub, not both" if !options[:swag].blank? && !options[:grub].blank?
31
+ raise ArgumentError, "must provide either :swag or :grub, not both" if !options[:swag].nil? && !options[:grub].nil?
31
32
  # if they provide neither
32
- raise ArgumentError, "must provide either :swag or :grub" if options[:swag].blank? && options[:grub].blank?
33
+ raise ArgumentError, "must provide either :swag or :grub" if options[:swag].nil? && options[:grub].nil?
33
34
  raise ArgumentError, ":swab is #{options[:swab].inspect}, but must be one of #{CsvPirate::BOOKIE.inspect}" unless CsvPirate::BOOKIE.include?(options[:swab])
34
35
  raise ArgumentError, ":mop is #{options[:mop].inspect}, but must be one of #{CsvPirate::MOP_HEADS.inspect}" unless CsvPirate::MOP_HEADS.include?(options[:mop])
35
36
  raise ArgumentError, ":gibbet is #{options[:gibbet].inspect}, and does not contain a '.' character, which is required when using iterative filenames (set :swab => :none to turn off iterative filenames)" if options[:swab] != :none && (options[:gibbet].nil? || !options[:gibbet].include?('.'))
@@ -41,6 +42,10 @@ module NinthBit
41
42
 
42
43
  extend ClassMethods unless (class << self; included_modules; end).include?(ClassMethods)
43
44
 
45
+ class << self
46
+ attr_accessor :piratey_options
47
+ end
48
+
44
49
  self.piratey_options = options
45
50
 
46
51
  end
@@ -58,10 +63,6 @@ module NinthBit
58
63
 
59
64
  module ClassMethods
60
65
 
61
- def self.extended(base)
62
- base.class_inheritable_accessor :piratey_options
63
- end
64
-
65
66
  # intended for use with send_data for downloading the text of the csv:
66
67
  # send_data Make.say_your_last_words
67
68
  # TODO: Fix say_your_last_words so it works! Use send_data args for real
@@ -103,6 +104,29 @@ module NinthBit
103
104
  CsvPirate.new(self.piratey_args(args))
104
105
  end
105
106
 
107
+ def weigh_anchor(args = {})
108
+ pargs = self.piratey_args(args)
109
+ pargs.merge!({
110
+ :gibbet => '.dump',
111
+ :chart => pargs[:chart] + ["dumps"],
112
+ })
113
+ CsvPirate.create(pargs)
114
+ end
115
+
116
+ def raise_anchor(args = {})
117
+ pargs = self.piratey_args(args)
118
+ pargs.merge!({
119
+ :chart => pargs[:chart] + ["dumps"],
120
+ :brigantine => :last
121
+ })
122
+ csv_pirate = CsvPirate.new(pargs)
123
+
124
+ csv_pirate.to_memory.map do |obj|
125
+ obj.save(false) if obj.respond_to?(:save)
126
+ obj
127
+ end
128
+ end
129
+
106
130
  protected
107
131
 
108
132
  def piratey_args(args = {})
@@ -110,7 +134,7 @@ module NinthBit
110
134
  return { :chart => args[:chart] || self.piratey_options[:chart],
111
135
  :aft => args[:aft] || self.piratey_options[:aft],
112
136
  :gibbet => args[:gibbet] || self.piratey_options[:gibbet],
113
- :chronometer => args[:chronometer] == false ? false : args[:chronometer] || Date.today,
137
+ :chronometer => get_chronometer(args[:chronometer]),
114
138
  :waggoner => args[:waggoner] || self.piratey_options[:waggoner] || "#{self}",
115
139
  :swag => args[:swag] || self.piratey_options[:swag],
116
140
  :swab => args[:swab] || self.piratey_options[:swab],
@@ -123,6 +147,14 @@ module NinthBit
123
147
  :bury_treasure => args[:bury_treasure] || self.piratey_options[:bury_treasure] }
124
148
  end
125
149
 
150
+ def get_chronometer(chron)
151
+ chron == false ?
152
+ false :
153
+ (chron || (self.piratey_options[:chronometer] == false ?
154
+ false :
155
+ (self.piratey_options[:chronometer] || Date.today)))
156
+ end
157
+
126
158
  end
127
159
 
128
160
  end
data/rails/init.rb CHANGED
@@ -1,4 +1,11 @@
1
- require 'faster_csv'
1
+ begin
2
+ require 'rubygems'
3
+ gem 'fastercsv'
4
+ rescue LoadError
5
+ "Unable to load dependencies: rubygems or fastercsv"
6
+ end
7
+
8
+ require 'faster_csv' unless defined?(FasterCSV)
2
9
  require 'csv_pirate'
3
10
  require 'ninth_bit/pirate_ship'
4
11
 
@@ -1,7 +1,195 @@
1
1
  require File.dirname(__FILE__) + '/spec_helper'
2
2
 
3
3
  describe "CsvPirate" do
4
- it "fails" do
5
- fail "hey buddy, you should probably rename this file and start specing for real"
4
+ describe "#initialize" do
5
+ before(:each) do
6
+ @csv_pirate = CsvPirate.new({
7
+ :grub => GlowingGasBall,
8
+ :spyglasses => [:get_stars],
9
+ :chart => ["spec","csv","GlowingGasBall"],
10
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
11
+ :chronometer => false,
12
+ :gibbet => "",
13
+ :aft => ".csv",
14
+ :swab => :none,
15
+ :mop => :clean,
16
+ :waggoner => 'data'
17
+ })
18
+ end
19
+
20
+ it "should return an instance of CsvPirate" do
21
+ @csv_pirate.class.should == CsvPirate
22
+ end
23
+
24
+ it "should not export anything" do
25
+ @csv_pirate.maroon.should == ""
26
+ end
6
27
  end
28
+
29
+ describe "#create" do
30
+ before(:each) do
31
+ @csv_pirate = CsvPirate.create({
32
+ :grub => GlowingGasBall,
33
+ :spyglasses => [:get_stars],
34
+ :chart => ["spec","csv","GlowingGasBall"],
35
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
36
+ :chronometer => false,
37
+ :gibbet => "",
38
+ :aft => ".csv",
39
+ :swab => :none,
40
+ :mop => :clean,
41
+ :waggoner => 'data'
42
+ })
43
+ end
44
+
45
+ it "should return an instance of CsvPirate" do
46
+ @csv_pirate.class.should == CsvPirate
47
+ end
48
+
49
+ it "should store export in maroon instance variable" do
50
+ @csv_pirate.maroon.should == "Name,Distance,Spectral type,Name hash,Name next,Name upcase,Star vowels\nProxima Centauri,4.2 LY,M5.5Vc,-1176188012,Proxima Centaurj,PROXIMA CENTAURI,Pr*x*m* C*nt**r*\nRigil Kentaurus,4.3 LY,G2V,1916094624,Rigil Kentaurut,RIGIL KENTAURUS,R*g*l K*nt**r*s\nBarnard's Star,5.9 LY,M3.8V,1003964756,Barnard's Stas,BARNARD'S STAR,B*rn*rd's St*r\nWolf 359,7.7 LY,M5.8Vc,-1717989858,Wolf 360,WOLF 359,W*lf 359\nLalande 21185,8.26 LY,M2V,466625069,Lalande 21186,LALANDE 21185,L*l*nd* 21185\nLuyten 726-8A and B,8.73 LY,M5.5 de & M6 Ve,1260790153,Luyten 726-8A and C,LUYTEN 726-8A AND B,L*yt*n 726-8A *nd B\nSirius A and B,8.6 LY,A1Vm,1177502705,Sirius A and C,SIRIUS A AND B,S*r**s A *nd B\nRoss 154,9.693 LY,M3.5,2120976706,Ross 155,ROSS 154,R*ss 154\nRoss 248,10.32 LY,M5.5V,2129428738,Ross 249,ROSS 248,R*ss 248\nEpsilon Eridani,10.5 LY,K2V,931307088,Epsilon Eridanj,EPSILON ERIDANI,Eps*l*n Er*d*n*\n"
51
+ end
52
+ end
53
+
54
+ describe "#hoist_mainstay" do
55
+ before(:each) do
56
+ @csv_pirate = CsvPirate.new({
57
+ :grub => GlowingGasBall,
58
+ :spyglasses => [:get_stars],
59
+ :chart => ["spec","csv","GlowingGasBall"],
60
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
61
+ :chronometer => false,
62
+ :gibbet => "",
63
+ :aft => ".csv",
64
+ :swab => :none,
65
+ :mop => :clean,
66
+ :waggoner => 'data'
67
+ })
68
+ end
69
+
70
+ it "should return an instance of String" do
71
+ @csv_pirate.hoist_mainstay.class.should == String
72
+ end
73
+
74
+ it "should return the export as a string" do
75
+ @csv_pirate.hoist_mainstay.should == "Name,Distance,Spectral type,Name hash,Name next,Name upcase,Star vowels\nProxima Centauri,4.2 LY,M5.5Vc,-1176188012,Proxima Centaurj,PROXIMA CENTAURI,Pr*x*m* C*nt**r*\nRigil Kentaurus,4.3 LY,G2V,1916094624,Rigil Kentaurut,RIGIL KENTAURUS,R*g*l K*nt**r*s\nBarnard's Star,5.9 LY,M3.8V,1003964756,Barnard's Stas,BARNARD'S STAR,B*rn*rd's St*r\nWolf 359,7.7 LY,M5.8Vc,-1717989858,Wolf 360,WOLF 359,W*lf 359\nLalande 21185,8.26 LY,M2V,466625069,Lalande 21186,LALANDE 21185,L*l*nd* 21185\nLuyten 726-8A and B,8.73 LY,M5.5 de & M6 Ve,1260790153,Luyten 726-8A and C,LUYTEN 726-8A AND B,L*yt*n 726-8A *nd B\nSirius A and B,8.6 LY,A1Vm,1177502705,Sirius A and C,SIRIUS A AND B,S*r**s A *nd B\nRoss 154,9.693 LY,M3.5,2120976706,Ross 155,ROSS 154,R*ss 154\nRoss 248,10.32 LY,M5.5V,2129428738,Ross 249,ROSS 248,R*ss 248\nEpsilon Eridani,10.5 LY,K2V,931307088,Epsilon Eridanj,EPSILON ERIDANI,Eps*l*n Er*d*n*\n"
76
+ end
77
+
78
+ it "should store export in maroon instance variable" do
79
+ @csv_pirate.maroon.should == ""
80
+ @csv_pirate.hoist_mainstay
81
+ @csv_pirate.maroon.should == "Name,Distance,Spectral type,Name hash,Name next,Name upcase,Star vowels\nProxima Centauri,4.2 LY,M5.5Vc,-1176188012,Proxima Centaurj,PROXIMA CENTAURI,Pr*x*m* C*nt**r*\nRigil Kentaurus,4.3 LY,G2V,1916094624,Rigil Kentaurut,RIGIL KENTAURUS,R*g*l K*nt**r*s\nBarnard's Star,5.9 LY,M3.8V,1003964756,Barnard's Stas,BARNARD'S STAR,B*rn*rd's St*r\nWolf 359,7.7 LY,M5.8Vc,-1717989858,Wolf 360,WOLF 359,W*lf 359\nLalande 21185,8.26 LY,M2V,466625069,Lalande 21186,LALANDE 21185,L*l*nd* 21185\nLuyten 726-8A and B,8.73 LY,M5.5 de & M6 Ve,1260790153,Luyten 726-8A and C,LUYTEN 726-8A AND B,L*yt*n 726-8A *nd B\nSirius A and B,8.6 LY,A1Vm,1177502705,Sirius A and C,SIRIUS A AND B,S*r**s A *nd B\nRoss 154,9.693 LY,M3.5,2120976706,Ross 155,ROSS 154,R*ss 154\nRoss 248,10.32 LY,M5.5V,2129428738,Ross 249,ROSS 248,R*ss 248\nEpsilon Eridani,10.5 LY,K2V,931307088,Epsilon Eridanj,EPSILON ERIDANI,Eps*l*n Er*d*n*\n"
82
+ end
83
+ end
84
+
85
+ describe "#old_csv_dump" do
86
+
87
+ before(:each) do
88
+ ["1/1/1998","2/2/2002","1/2/2003","3/2/2001","2/1/2007"].map {|x| Date.parse(x)}.each do |date|
89
+ @csv_pirate = CsvPirate.new({
90
+ :grub => GlowingGasBall,
91
+ :spyglasses => [:get_stars],
92
+ :chart => ["spec","csv","GlowingGasBall","dumps"],
93
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
94
+ :chronometer => date,
95
+ :swab => :none,
96
+ :mop => :clean
97
+ })
98
+ @csv_pirate.hoist_mainstay
99
+ end
100
+ end
101
+
102
+ it "should find first (oldest) dump" do
103
+ @new_csv_pirate = CsvPirate.new({
104
+ :grub => GlowingGasBall,
105
+ :spyglasses => [:get_stars],
106
+ :chart => ["spec","csv","GlowingGasBall","dumps"],
107
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
108
+ :chronometer => false,
109
+ :brigantine => :first,
110
+ :swab => :none,
111
+ :mop => :clean
112
+ })
113
+ @new_csv_pirate.brigantine.should == "spec/csv/GlowingGasBall/dumps/GlowingGasBall.19980101.export.csv"
114
+ end
115
+
116
+ it "should find last (newest) dump" do
117
+ @new_csv_pirate = CsvPirate.new({
118
+ :grub => GlowingGasBall,
119
+ :spyglasses => [:get_stars],
120
+ :chart => ["spec","csv","GlowingGasBall","dumps"],
121
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
122
+ :chronometer => false,
123
+ :brigantine => :last,
124
+ :swab => :none,
125
+ :mop => :clean
126
+ })
127
+ @new_csv_pirate.brigantine.should == "spec/csv/GlowingGasBall/dumps/GlowingGasBall.20070201.export.csv"
128
+ end
129
+ end
130
+
131
+ describe "#to_memory" do
132
+
133
+ before(:each) do
134
+ ["1/1/1998","2/2/2002","1/2/2003","3/2/2001","2/1/2007"].map {|x| Date.parse(x)}.each do |date|
135
+ @csv_pirate = CsvPirate.new({
136
+ :grub => GlowingGasBall,
137
+ :spyglasses => [:get_stars],
138
+ :chart => ["spec","csv","GlowingGasBall","dumps"],
139
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
140
+ :chronometer => date,
141
+ :swab => :none,
142
+ :mop => :clean
143
+ })
144
+ @csv_pirate.hoist_mainstay
145
+ end
146
+ end
147
+
148
+ it "should return an array of 10 grubs built from data in CSV" do
149
+ @new_csv_pirate = CsvPirate.new({
150
+ :grub => GlowingGasBall,
151
+ :spyglasses => [:get_stars],
152
+ :chart => ["spec","csv","GlowingGasBall","dumps"],
153
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
154
+ :chronometer => false,
155
+ :brigantine => :last,
156
+ :swab => :none,
157
+ :mop => :clean
158
+ })
159
+ @new_csv_pirate.brigantine.should == "spec/csv/GlowingGasBall/dumps/GlowingGasBall.20070201.export.csv"
160
+ @new_csv_pirate.to_memory.class.should == Array
161
+ @new_csv_pirate.to_memory.length.should == 10
162
+ end
163
+ end
164
+
165
+ describe ":blackjack option" do
166
+ before(:each) do
167
+ @csv_pirate = CsvPirate.new({
168
+ :grub => GlowingGasBall,
169
+ :spyglasses => [:get_stars],
170
+ :chart => ["spec","csv","GlowingGasBall"],
171
+ :booty => [:name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
172
+ :chronometer => false,
173
+ :gibbet => "",
174
+ :aft => ".csv",
175
+ :swab => :none,
176
+ :mop => :clean,
177
+ :waggoner => 'data'
178
+ })
179
+ end
180
+
181
+ it "should be {humanize => '_'} by default" do
182
+ @csv_pirate.blackjack.should == {:humanize => '_'}
183
+ @csv_pirate.hoist_mainstay
184
+ @csv_pirate.maroon.should == "Name,Distance,Spectral type,Name hash,Name next,Name upcase,Star vowels\nProxima Centauri,4.2 LY,M5.5Vc,-1176188012,Proxima Centaurj,PROXIMA CENTAURI,Pr*x*m* C*nt**r*\nRigil Kentaurus,4.3 LY,G2V,1916094624,Rigil Kentaurut,RIGIL KENTAURUS,R*g*l K*nt**r*s\nBarnard's Star,5.9 LY,M3.8V,1003964756,Barnard's Stas,BARNARD'S STAR,B*rn*rd's St*r\nWolf 359,7.7 LY,M5.8Vc,-1717989858,Wolf 360,WOLF 359,W*lf 359\nLalande 21185,8.26 LY,M2V,466625069,Lalande 21186,LALANDE 21185,L*l*nd* 21185\nLuyten 726-8A and B,8.73 LY,M5.5 de & M6 Ve,1260790153,Luyten 726-8A and C,LUYTEN 726-8A AND B,L*yt*n 726-8A *nd B\nSirius A and B,8.6 LY,A1Vm,1177502705,Sirius A and C,SIRIUS A AND B,S*r**s A *nd B\nRoss 154,9.693 LY,M3.5,2120976706,Ross 155,ROSS 154,R*ss 154\nRoss 248,10.32 LY,M5.5V,2129428738,Ross 249,ROSS 248,R*ss 248\nEpsilon Eridani,10.5 LY,K2V,931307088,Epsilon Eridanj,EPSILON ERIDANI,Eps*l*n Er*d*n*\n"
185
+ end
186
+
187
+ it "should work as {:join => '_'}" do
188
+ @csv_pirate.blackjack = {:join => '_'}
189
+ @csv_pirate.blackjack.should == {:join => '_'}
190
+ @csv_pirate.hoist_mainstay
191
+ @csv_pirate.maroon.should == "name,distance,spectral_type,name_hash,name_next,name_upcase,star_vowels\nProxima Centauri,4.2 LY,M5.5Vc,-1176188012,Proxima Centaurj,PROXIMA CENTAURI,Pr*x*m* C*nt**r*\nRigil Kentaurus,4.3 LY,G2V,1916094624,Rigil Kentaurut,RIGIL KENTAURUS,R*g*l K*nt**r*s\nBarnard's Star,5.9 LY,M3.8V,1003964756,Barnard's Stas,BARNARD'S STAR,B*rn*rd's St*r\nWolf 359,7.7 LY,M5.8Vc,-1717989858,Wolf 360,WOLF 359,W*lf 359\nLalande 21185,8.26 LY,M2V,466625069,Lalande 21186,LALANDE 21185,L*l*nd* 21185\nLuyten 726-8A and B,8.73 LY,M5.5 de & M6 Ve,1260790153,Luyten 726-8A and C,LUYTEN 726-8A AND B,L*yt*n 726-8A *nd B\nSirius A and B,8.6 LY,A1Vm,1177502705,Sirius A and C,SIRIUS A AND B,S*r**s A *nd B\nRoss 154,9.693 LY,M3.5,2120976706,Ross 155,ROSS 154,R*ss 154\nRoss 248,10.32 LY,M5.5V,2129428738,Ross 249,ROSS 248,R*ss 248\nEpsilon Eridani,10.5 LY,K2V,931307088,Epsilon Eridanj,EPSILON ERIDANI,Eps*l*n Er*d*n*\n"
192
+ end
193
+ end
194
+
7
195
  end
@@ -0,0 +1,69 @@
1
+ require File.dirname(__FILE__) + '/spec_helper'
2
+
3
+ describe "PirateShip" do
4
+ describe "#walk_the_plank" do
5
+ before(:each) do
6
+ @csv_pirate = Star.walk_the_plank
7
+ end
8
+
9
+ it "should return a string" do
10
+ @csv_pirate.class.should == String
11
+ end
12
+ end
13
+
14
+ describe "#blindfold" do
15
+ before(:each) do
16
+ @csv_pirate = Star.blindfold
17
+ end
18
+
19
+ it "should return an instance of CsvPirate" do
20
+ @csv_pirate.class.should == CsvPirate
21
+ end
22
+ end
23
+
24
+ describe "#land_ho" do
25
+ before(:each) do
26
+ @csv_pirate = Star.land_ho
27
+ end
28
+
29
+ it "should return an instance of CsvPirate" do
30
+ @csv_pirate.class.should == CsvPirate
31
+ end
32
+ end
33
+
34
+ describe "#land_ho" do
35
+ before(:each) do
36
+ @csv_pirate = Star.land_ho
37
+ end
38
+
39
+ it "should return an instance of CsvPirate" do
40
+ @csv_pirate.class.should == CsvPirate
41
+ end
42
+ end
43
+
44
+ describe "#weigh_anchor" do
45
+ before(:each) do
46
+ @csv_pirate = Star.weigh_anchor({:chronometer => Date.parse("2/1/2007")})
47
+ end
48
+
49
+ it "should return an instance of CsvPirate" do
50
+ @csv_pirate.class.should == CsvPirate
51
+ @csv_pirate.chart.should == ["spec","csv","Star","dumps"]
52
+ end
53
+ end
54
+
55
+ describe "#raise_anchor" do
56
+ before(:each) do
57
+ @csv_pirate = Star.weigh_anchor({:chronometer => Date.parse("3/29/2002")})
58
+ @csv_pirate = Star.weigh_anchor({:chronometer => Date.parse("6/14/2004")})
59
+ @csv_pirate = Star.weigh_anchor({:chronometer => Date.parse("12/25/1962")})
60
+ @csv_pirate = Star.raise_anchor()
61
+ end
62
+
63
+ it "should return an array of 10 grubs built from data in CSV" do
64
+ @csv_pirate.class.should == Array
65
+ @csv_pirate.length.should == 10
66
+ end
67
+ end
68
+
69
+ end
data/spec/spec.opts ADDED
@@ -0,0 +1,7 @@
1
+ --colour
2
+ --format
3
+ specdoc
4
+ --loadby
5
+ mtime
6
+ --reverse
7
+ --backtrace
data/spec/spec_helper.rb CHANGED
@@ -2,8 +2,11 @@ require 'spec'
2
2
 
3
3
  $LOAD_PATH.unshift(File.dirname(__FILE__))
4
4
 
5
- require 'csv_pirate'
5
+ require 'init'
6
6
 
7
7
  Spec::Runner.configure do |config|
8
8
 
9
9
  end
10
+
11
+ # require all files inside spec_helpers
12
+ Dir[File.join(File.dirname(__FILE__), "spec_helpers/*.rb")].each { |file| require file }
@@ -0,0 +1,30 @@
1
+ class GlowingGasBall
2
+
3
+ attr_accessor :name, :distance, :spectral_type
4
+
5
+ def initialize(*args)
6
+ @name = args.first[:name]
7
+ @distance = args.first[:distance]
8
+ @spectral_type = args.first[:spectral_type]
9
+ end
10
+
11
+ def star_vowels
12
+ self.name.tr('aeiou', '*')
13
+ end
14
+
15
+ def self.get_stars
16
+ [
17
+ GlowingGasBall.new(:name => "Proxima Centauri", :distance => "4.2 LY", :spectral_type => "M5.5Vc"),
18
+ GlowingGasBall.new(:name => "Rigil Kentaurus", :distance => "4.3 LY", :spectral_type => "G2V"),
19
+ GlowingGasBall.new(:name => "Barnard's Star", :distance => "5.9 LY", :spectral_type => "M3.8V"),
20
+ GlowingGasBall.new(:name => "Wolf 359", :distance => "7.7 LY", :spectral_type => "M5.8Vc"),
21
+ GlowingGasBall.new(:name => "Lalande 21185", :distance => "8.26 LY", :spectral_type => "M2V"),
22
+ GlowingGasBall.new(:name => "Luyten 726-8A and B", :distance => "8.73 LY", :spectral_type => "M5.5 de & M6 Ve"),
23
+ GlowingGasBall.new(:name => "Sirius A and B", :distance => "8.6 LY", :spectral_type => "A1Vm"),
24
+ GlowingGasBall.new(:name => "Ross 154", :distance => "9.693 LY", :spectral_type => "M3.5"),
25
+ GlowingGasBall.new(:name => "Ross 248", :distance => "10.32 LY", :spectral_type => "M5.5V"),
26
+ GlowingGasBall.new(:name => "Epsilon Eridani", :distance => "10.5 LY", :spectral_type => "K2V")
27
+ ]
28
+ end
29
+
30
+ end
@@ -0,0 +1,29 @@
1
+ class Star < GlowingGasBall
2
+
3
+ extend NinthBit::PirateShip::ActMethods
4
+ has_csv_pirate_ship :booty => [ :name, :distance, :spectral_type, {:name => :hash}, {:name => :next}, {:name => :upcase}, :star_vowels ],
5
+ :spyglasses => [:get_stars],
6
+ :chart => ["spec","csv","Star"],
7
+ :chronometer => false,
8
+ :gibbet => "",
9
+ :aft => ".csv",
10
+ :swab => :none,
11
+ :mop => :clean,
12
+ :waggoner => 'data'
13
+
14
+ def self.get_stars
15
+ [
16
+ Star.new(:name => "Proxima Centauri", :distance => "4.2 LY", :spectral_type => "M5.5Vc"),
17
+ Star.new(:name => "Rigil Kentaurus", :distance => "4.3 LY", :spectral_type => "G2V"),
18
+ Star.new(:name => "Barnard's Star", :distance => "5.9 LY", :spectral_type => "M3.8V"),
19
+ Star.new(:name => "Wolf 359", :distance => "7.7 LY", :spectral_type => "M5.8Vc"),
20
+ Star.new(:name => "Lalande 21185", :distance => "8.26 LY", :spectral_type => "M2V"),
21
+ Star.new(:name => "Luyten 726-8A and B", :distance => "8.73 LY", :spectral_type => "M5.5 de & M6 Ve"),
22
+ Star.new(:name => "Sirius A and B", :distance => "8.6 LY", :spectral_type => "A1Vm"),
23
+ Star.new(:name => "Ross 154", :distance => "9.693 LY", :spectral_type => "M3.5"),
24
+ Star.new(:name => "Ross 248", :distance => "10.32 LY", :spectral_type => "M5.5V"),
25
+ Star.new(:name => "Epsilon Eridani", :distance => "10.5 LY", :spectral_type => "K2V")
26
+ ]
27
+ end
28
+
29
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: csv_pirate
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.4.4
4
+ version: 4.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Peter Boling
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2009-11-10 00:00:00 -05:00
12
+ date: 2010-01-15 00:00:00 -05:00
13
13
  default_executable:
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
@@ -23,7 +23,7 @@ dependencies:
23
23
  version: "0"
24
24
  version:
25
25
  description: |-
26
- CsvPirate is the easy way to create a CSV of essentially anything in Rails, in full pirate regalia.
26
+ CsvPirate is the easy way to create a CSV of essentially anything in Ruby, in full pirate regalia.
27
27
  It works better if you are wearing a tricorne!
28
28
  email: peter.boling@gmail.com
29
29
  executables: []
@@ -45,6 +45,12 @@ files:
45
45
  - lib/csv_pirate.rb
46
46
  - lib/ninth_bit/pirate_ship.rb
47
47
  - rails/init.rb
48
+ - spec/csv_pirate_spec.rb
49
+ - spec/pirate_ship_spec.rb
50
+ - spec/spec.opts
51
+ - spec/spec_helper.rb
52
+ - spec/spec_helpers/glowing_gas_ball.rb
53
+ - spec/spec_helpers/star.rb
48
54
  has_rdoc: true
49
55
  homepage: http://github.com/pboling/csv_pirate
50
56
  licenses: []
@@ -72,7 +78,10 @@ rubyforge_project:
72
78
  rubygems_version: 1.3.5
73
79
  signing_key:
74
80
  specification_version: 3
75
- summary: Easily create CSVs of any data that can be derived from your models (using pirates!).
81
+ summary: Easily create CSVs of any data that can be derived from instance methods on your classes.
76
82
  test_files:
77
83
  - spec/csv_pirate_spec.rb
84
+ - spec/pirate_ship_spec.rb
78
85
  - spec/spec_helper.rb
86
+ - spec/spec_helpers/glowing_gas_ball.rb
87
+ - spec/spec_helpers/star.rb