ruport 0.4.4 → 0.4.5

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.
data/AUTHORS CHANGED
@@ -12,3 +12,10 @@ Parse::Input which is the base for Ruport::Parser
12
12
 
13
13
  Francis Hwang:
14
14
  SQLSplit
15
+
16
+ Simon Claret:
17
+ PDF table support for Format::Builder
18
+
19
+ Dudley Flanders:
20
+ DataSet improvements
21
+
data/CHANGELOG CHANGED
@@ -1,4 +1,27 @@
1
- The current version of Ruby Reports is 0.4.4
1
+ The current version of Ruby Reports is 0.4.5 (Developmental)
2
+
3
+ changes since 0.4.4:
4
+
5
+ - DataRow constructor now matches DataSet style.
6
+
7
+ - DataSet picked up a ton of array-like functionality
8
+
9
+ - DataSet#load now optionally accepts a block that acts something
10
+ like inject.
11
+
12
+ - Added a DataSet#select_columns!() method
13
+
14
+ - What the heck was Format#filter_ruby? It's gone now
15
+
16
+ - DataSet#as() now hooked to the new formatting system.
17
+ note API breakage in block forms
18
+
19
+ - DataSet set operations (DF)
20
+
21
+ - Much smarter DataSet#<< (Dudley Flanders)
22
+
23
+ - Ruport now has pseudo keyword support in DataSets.
24
+ (Thanks to Dudley Flanders!)
2
25
 
3
26
  changes since 0.4.2:
4
27
 
data/Rakefile CHANGED
@@ -21,7 +21,7 @@ end
21
21
 
22
22
  spec = Gem::Specification.new do |spec|
23
23
  spec.name = LEAN ? "ruport-lean" : "ruport"
24
- spec.version = "0.4.4"
24
+ spec.version = "0.4.5"
25
25
  spec.platform = Gem::Platform::RUBY
26
26
  spec.summary = "A generalized Ruby report generation and templating engine."
27
27
  spec.files = Dir.glob("{examples,lib,test}/**/**/*") +
data/TODO CHANGED
@@ -21,19 +21,16 @@ Immediate Goals:
21
21
 
22
22
  - Value modification predicate.
23
23
  DataRow#set_value_if("my_value") { # my_condition }
24
-
24
+ (Update: What was I talking about here???)
25
+
25
26
  - Column based default values
26
27
 
27
28
  - Integrate Ruport::Parser into Report#parse and Format#parser
28
29
 
29
30
  - Document the inner classes of Format
30
31
 
31
- - Get unit tests up to 100% coverage
32
-
33
32
  - make the Fetchable module to abstract data acquisition
34
33
 
35
- - DataSet subclasses Array
36
-
37
34
  - Calculated fields
38
35
 
39
36
  Other High Priority Goals:
@@ -14,7 +14,7 @@ module Ruport
14
14
 
15
15
  begin; require 'rubygems'; rescue LoadError; nil end
16
16
 
17
- VERSION = "Ruby Reports Version 0.4.4"
17
+ VERSION = "Ruby Reports Version 0.4.5 (Developmental)"
18
18
 
19
19
  # Ruports logging and error interface.
20
20
  # Can generate warnings or raise fatal errors
@@ -12,8 +12,8 @@
12
12
  # ++
13
13
  module Ruport
14
14
 
15
- # DataRows are Enumerable lists which can be accessed by field name or ordinal
16
- # position.
15
+ # DataRows are Enumerable lists which can be accessed by field name or
16
+ # ordinal position.
17
17
  #
18
18
  # They feature a tagging system, allowing them to be easily
19
19
  # compared or recalled.
@@ -24,38 +24,37 @@ module Ruport
24
24
 
25
25
  include Enumerable
26
26
 
27
- # Takes data and field names as well as some optional parameters and
27
+ # Takes field names as well as some optional parameters and
28
28
  # constructs a DataRow.
29
- #
30
- #
31
- # <tt>data</tt> can be specified in Hash, Array, or DataRow form
32
29
  #
33
30
  # Options:
34
- # <tt>:filler</tt>:: this will be used as a default value for empty
35
- # <tt>:tags</tt>:: an initial set of tags for the row
31
+ # <tt>:data</tt>:: can be specified in Hash, Array, or DataRow form
32
+ # <tt>:default</tt>:: The default value for empty fields
33
+ # <tt>:tags</tt>:: an initial set of tags for the row
36
34
  #
37
35
  #
38
36
  # Examples:
39
- # >> Ruport::DataRow.new [1,2,3,4,5], [:a,:b,:c,:d,:e],
37
+ # >> Ruport::DataRow.new [:a,:b,:c,:d,:e], :data => [1,2,3,4,5]
40
38
  # :tags => %w[cat dog]
41
39
  # => #<Ruport::DataRow:0xb77e4b04 @fields=[:a, :b, :c, :d, :e],
42
40
  # @data=[1, 2, 3, 4, 5], @tags=["cat", "dog"]>
43
41
  #
44
- # >> Ruport::DataRow.new({ :a => 'moo', :c => 'caw'} , [:a,:b,:c,:d,:e],
42
+ # >> Ruport::DataRow.new([:a,:b,:c,:d,:e],
43
+ # :data => { :a => 'moo', :c => 'caw'} ,
45
44
  # :tags => %w[cat dog])
46
45
  # => #<Ruport::DataRow:0xb77c298c @fields=[:a, :b, :c, :d, :e],
47
46
  # @data=["moo", nil, "caw", nil, nil], @tags=["cat", "dog"]>
48
47
  #
49
- # >> Ruport::DataRow.new [1,2,3], [:a,:b,:c,:d,:e], :tags => %w[cat dog],
50
- # :filler => 0
48
+ # >> Ruport::DataRow.new [:a,:b,:c,:d,:e], :data => [1,2,3],
49
+ # :tags => %w[cat dog], :default => 0
51
50
  # => #<Ruport::DataRow:0xb77bb4d4 @fields=[:a, :b, :c, :d, :e],
52
51
  # @data=[1, 2, 3, 0, 0], @tags=["cat", "dog"]>
53
52
  #
54
- def initialize( data, fields, options={} )
53
+ def initialize(fields, options={})
55
54
 
56
55
  #checks to ensure data is convertable
57
- verify data
58
- data = data.dup
56
+ verify options[:data]
57
+ data = options[:data].dup
59
58
 
60
59
  @fields = fields.dup
61
60
  @tags = (options[:tags] || {}).dup
@@ -63,22 +62,21 @@ module Ruport
63
62
 
64
63
  nr_action = case(data)
65
64
  when Array
66
- lambda { |key, index| @data[index] = data.shift || options[:filler] }
65
+ lambda {|key, index| @data[index] = data.shift || options[:default]}
67
66
  when DataRow
68
- lambda { |key, index| @data = data.to_a }
67
+ lambda {|key, index| @data = data.to_a}
69
68
  else
70
- lambda { |key, index| @data[index] = data[key] || options[:filler] }
69
+ lambda {|key, index| @data[index] = data[key] || options[:default]}
71
70
  end
72
- @fields.each_with_index { |key, index| nr_action.call(key,index) }
71
+ @fields.each_with_index {|key, index| nr_action.call(key,index)}
73
72
  end
74
73
 
75
74
 
76
75
  attr_accessor :fields, :tags
77
76
 
78
- # Returns an array of values. Should probably return a DataRow.
79
- # Loses field information.
77
+ # Returns a new DataRow
80
78
  def +(other)
81
- DataRow.new @data + other.to_a, @fields + other.fields
79
+ DataRow.new @fields + other.fields, :data => (@data + other.to_a)
82
80
  end
83
81
 
84
82
  # Lets you access individual fields
@@ -164,7 +162,7 @@ module Ruport
164
162
  end
165
163
 
166
164
  def clone
167
- self.class.new @data, @fields, :tags => @tags
165
+ self.class.new @fields, :data => @data, :tags => @tags
168
166
  end
169
167
 
170
168
  alias_method :dup, :clone
@@ -1,9 +1,11 @@
1
1
  # data_set.rb : Ruby Reports core datastructure.
2
2
  #
3
3
  # Author: Gregory T. Brown (gregory.t.brown at gmail dot com)
4
- #
5
4
  # Copyright (c) 2006, All Rights Reserved.
6
5
  #
6
+ # Pseudo keyword argument support, improved <<, and set operations submitted by
7
+ # Dudley Flanders
8
+ #
7
9
  # This is free software. You may modify and redistribute this freely under
8
10
  # your choice of the GNU General Public License or the Ruby License.
9
11
  #
@@ -15,42 +17,12 @@ module Ruport
15
17
  # and user-defined sets of data.
16
18
  #
17
19
  # It is tightly integrated with Ruport's formatting and query systems, so if
18
- # you'd like to take advantage of these models, you will probably find DataSet
19
- # useful.
20
- #
21
- # Sample Usage:
22
- #
23
- # my_data = [[1,2,3],[4,5,6],[7,8,9]]
24
- #
25
- # ds = Ruport::DataSet.new([:col1, :col2, :col3],my_data)
26
- # ds << [ 10, 11, 12]
27
- # ds << { :col3 => 15, :col1 => 13, :col2 => 14 }
28
- # puts ds.select_columns(:col1, :col3).to_csv
29
- #
30
- # Output:
31
- #
32
- # col1,col3
33
- # 1,3
34
- # 4,6
35
- # 7,9
36
- # 10,12
37
- # 13,15
38
- #
39
- # The wild and crazy might want to try the Array hack:
40
- #
41
- # puts [[1,2,3],[4,5,6],[7,8,9]].to_ds(%w[col1 col2 col3])
42
- #
43
- # Output:
44
- #
45
- # fields: ( col1, col2, col3 )
46
- # row0: ( 1, 2, 3 )
47
- # row1: ( 4, 5, 6 )
48
- # row2: ( 7, 8, 9 )
49
- #
20
+ # you'd like to take advantage of these models, you will probably find
21
+ # DataSet useful.
50
22
  class DataSet
51
23
  #FIXME: Add logging to this class
52
24
  include Enumerable
53
-
25
+ extend Forwardable
54
26
  # DataSets must be given a set of fields to be defined.
55
27
  #
56
28
  # These field names will define the columns for the DataSet and how you
@@ -58,17 +30,19 @@ module Ruport
58
30
  #
59
31
  # data = Ruport::DataSet.new %w[ id name phone ]
60
32
  #
61
- # You can optionally pass in some content as well. (Must be Enumerable)
33
+ # Options:
34
+ # * <tt>:data</tt> - An Enumerable with the content for this DataSet
35
+ # * <tt>:default</tt> - The default value for empty cells
62
36
  #
63
- # content = [ %w[ a1 gregory 203-525-0523 ],
64
- # %w[ a2 james 555-555-5555 ] ]
65
37
  #
66
- # data = Ruport::DataSet.new(%w[ id name phone],content)
67
- def initialize(fields=[], content=nil, default=nil)
38
+ # DataSet supports the following Array methods through delegators
39
+ # length, empty?, delete_at, first, last, pop
40
+ #
41
+ def initialize(fields=[], options={})
68
42
  @fields = fields
43
+ @default = options[:default] || default
69
44
  @data = []
70
- @default = default
71
- content.each { |r| self << r } if content
45
+ options[:data].each { |r| self << r } if options[:data]
72
46
  end
73
47
 
74
48
  #an array which contains column names
@@ -79,35 +53,59 @@ module Ruport
79
53
 
80
54
  #data holds the elements of the Row
81
55
  attr_reader :data
82
-
56
+
57
+ def_delegators :@data, :length, :[], :empty?,
58
+ :delete_at, :first, :last, :pop,
59
+ :each, :reverse_each, :at, :clear
60
+
61
+ def delete_if(&block)
62
+ @data.delete_if &block; self
63
+ end
64
+
83
65
  #provides a deep copy of the DataSet.
84
66
  def clone
85
- DataSet.new(@fields,@data)
67
+ self.class.new(@fields, :data => @data)
86
68
  end
87
69
 
88
- #Allows ordinal access to rows
89
- #
90
- # my_data[2] -> Ruport::DataRow
91
- def [](index)
92
- @data[index]
70
+ # Creates a new DataSet with the same shape as this one, but empty.
71
+ def empty_clone
72
+ self.class.new(@fields)
93
73
  end
94
-
95
- #allows setting of rows (providing a DataRow is passed in)
74
+
75
+ #allows setting of rows
96
76
  def []=(index,data)
97
- @data[index] = DataRow.new data, @fields
77
+ @data[index] = DataRow.new @fields, :data => data
78
+ end
79
+
80
+ def [](index)
81
+ case(index)
82
+ when Range
83
+ self.class.new @fields, :data => @data[index]
84
+ else
85
+ @data[index]
86
+ end
98
87
  end
99
88
 
100
- # appends a row to the DataSet
101
- # can be added as an array or a keyed hash-like object.
89
+ # Appends a row to the DataSet
90
+ # Can be added as an array, an array of DataRows, a DataRow, or a keyed
91
+ # hash-like object.
102
92
  #
103
93
  # Columns left undefined will be filled with DataSet#default values.
104
94
  #
105
95
  # data << [ 1, 2, 3 ]
106
96
  # data << { :some_field_name => 3, :other => 2, :another => 1 }
107
97
  def << ( stuff, filler=@default )
108
- @data << DataRow.new(stuff,@fields,:filler => filler); self;
98
+ if stuff.kind_of?(DataRow)
99
+ @data << stuff
100
+ elsif stuff.kind_of?(Array) && stuff[0].kind_of?(DataRow)
101
+ @data.concat(stuff)
102
+ else
103
+ @data << DataRow.new(@fields, :data => stuff,:default => filler)
104
+ end
105
+ return self
109
106
  end
110
-
107
+ alias_method :push, :<<
108
+
111
109
  # checks if one dataset equals another
112
110
  # FIXME: expand this doc.
113
111
  def eql?(data2)
@@ -127,10 +125,38 @@ module Ruport
127
125
  eql?(data2)
128
126
  end
129
127
 
130
- # Returns true if DataSet contains no rows, false otherwise.
131
- def empty?
132
- return @data.empty?
128
+ # Set union - returns a DataSet with the elements that are contained in
129
+ # in either of the two given sets, with no duplicates.
130
+ def |(other)
131
+ clone << other.reject { |x| self.include? x }
132
+ end
133
+ alias_method :union, :|
134
+
135
+ # Set intersection
136
+ def &(other)
137
+ empty_clone << select { |x| other.include? x }
138
+ end
139
+ alias_method :intersection, :&
140
+
141
+ # Set difference
142
+ def -(other)
143
+ empty_clone << reject { |x| other.include? x }
144
+ end
145
+ alias_method :difference, :-
146
+
147
+ # Checks if one DataSet has the same set of fields as another
148
+ def shaped_like?(other)
149
+ return true if @fields.eql?(other.fields)
150
+ end
151
+
152
+ # Concatenates one DataSet onto another if they have the same shape
153
+ def concat(other)
154
+ if other.shaped_like?(self)
155
+ @data.concat(other.data)
156
+ return self
157
+ end
133
158
  end
159
+ alias_method :+, :concat
134
160
 
135
161
  # Allows loading of CSV files or YAML dumps. Returns a DataSet
136
162
  #
@@ -139,34 +165,44 @@ module Ruport
139
165
  # my_data = Ruport::DataSet.load("foo.csv")
140
166
  # my_data = Ruport::DataSet.load("foo.yaml")
141
167
  # my_data = Ruport::DataSet.load("foo.yml")
142
- def self.load ( source, default="")
168
+ def self.load ( source, default="", &block)
143
169
  case source
144
170
  when /\.(yaml|yml)/
145
171
  return YAML.load(File.open(source))
146
172
  when /\.csv/
147
- csv_klass = defined?(FasterCSV) ? FasterCSV : CSV
148
- input = csv_klass.read(source) if source =~ /\.csv/
173
+ require "fastercsv"
174
+ input = FasterCSV.read(source) if source =~ /\.csv/
149
175
  loaded_data = self.new
176
+
177
+ action = if block_given?
178
+ lambda { |r| block[loaded_data,r] }
179
+ else
180
+ lambda { |r| loaded_data << r }
181
+ end
182
+
150
183
  loaded_data.fields = input[0]
151
184
  loaded_data.default = default
152
- input[1..-1].each { |row| loaded_data << row }
185
+ input[1..-1].each { |row| action[row] }
153
186
  return loaded_data
154
187
  else
155
188
  raise "Invalid file type"
156
189
  end
157
190
  end
158
191
 
159
- # Iterates through the rows, yielding a DataRow for each.
160
- def each(&action)
161
- @data.each(&action)
162
- end
163
192
 
164
193
  # Returns a new DataSet composed of the fields specified.
165
194
  def select_columns(*fields)
166
195
  rows = fields.inject([]) { |s,e| s << map { |row| row[e] } }.transpose
167
- my_data = DataSet.new(fields,rows)
196
+ my_data = DataSet.new(fields, :data => rows)
168
197
  end
169
198
 
199
+ # Prunes the dataset to contain only the fields specified. (DESTRUCTIVE)
200
+ def select_columns!(*fields)
201
+ a = select_columns(*fields)
202
+ @fields = a.fields; @data = a.data
203
+ end
204
+
205
+
170
206
  # Returns a new DataSet with the specified fields removed
171
207
  def remove_columns(*fields)
172
208
  select_columns(*(@fields-fields))
@@ -193,10 +229,9 @@ module Ruport
193
229
  #
194
230
  # This will enable <tt>data.as(:my_format_name)</tt>
195
231
  def as(format,&action)
196
- builder = Format::Builder.new( self )
197
- builder.format = format
198
- action.call(builder) if block_given?
199
- builder.render
232
+ t = Format.table_object(:data => clone, :plugin => format)
233
+ action.call(t) if block_given?
234
+ t.render
200
235
  end
201
236
 
202
237
  # Will iterate row by row yielding each row
@@ -210,6 +245,11 @@ module Ruport
210
245
  end
211
246
 
212
247
  alias_method :sum, :sigma
248
+
249
+ # Converts a DataSet to an array of arrays
250
+ def to_a
251
+ @data.map {|x| x.to_a }
252
+ end
213
253
 
214
254
  # Converts a DataSet to CSV
215
255
  def to_csv; as(:csv) end
@@ -219,11 +259,6 @@ module Ruport
219
259
 
220
260
  # Readable string representation of the DataSet
221
261
  def to_s; as(:text) end
222
-
223
- def clone
224
- self.class.new @fields.dup, @data.dup, @default
225
- end
226
-
227
262
 
228
263
  end
229
264
  end
@@ -232,8 +267,7 @@ class Array
232
267
 
233
268
  # Will convert Arrays of Enumerable objects to DataSets.
234
269
  # May have dragons.
235
- def to_ds(fields,default=nil)
236
- Ruport::DataSet.new(fields,to_a,default)
237
- end
238
-
270
+ def to_ds(fields,options={})
271
+ Ruport::DataSet.new fields, :data => to_a, :default => options[:default]
272
+ end
239
273
  end
@@ -112,22 +112,15 @@ module Ruport
112
112
  # Processes the ERB text in <tt>@content</tt> in the context
113
113
  # of the object that Format is bound to.
114
114
  def filter_erb
115
- ERB.new(@content).result(@binding)
115
+ self.class.document :data => @content,
116
+ :klass_binding => @binding,
117
+ :plugin => :text
116
118
  end
117
119
 
118
120
  # Processes the RedCloth text in <tt>@content</tt> in the context
119
121
  # of the object that Format is bound to.
120
122
  def filter_red_cloth
121
- require "redcloth"
122
- RedCloth.new(@content).to_html
123
- end
124
-
125
- # Processes the ruby code in <tt>@content</tt> in the context
126
- # of the object that Format is bound to.
127
- #
128
- # (Does an eval on the binding)
129
- def filter_ruby
130
- eval(@content,@binding)
123
+ self.class.document :data => @content, :plugin => :html
131
124
  end
132
125
 
133
126
  # Takes a name and a block and creates a filter method
@@ -120,6 +120,7 @@ module Ruport
120
120
  attr_accessor :erb_enabled
121
121
 
122
122
  def apply_red_cloth
123
+ require "redcloth"
123
124
  active_plugin.data = RedCloth.new(active_plugin.data).to_html
124
125
  end
125
126
 
@@ -60,6 +60,11 @@ module Ruport
60
60
  end
61
61
 
62
62
  class TextPlugin < Format::Plugin
63
+
64
+ rendering_options :erb_enabled => true, :red_cloth_enabled => false
65
+
66
+ renderer :document
67
+
63
68
  renderer :table do
64
69
  data.inject(rendered_field_names){ |s,r|
65
70
  s << " #{r.to_a.join(' | ')} \n"
@@ -70,6 +75,7 @@ module Ruport
70
75
  end
71
76
 
72
77
  register_on :table_engine
78
+ register_on :document_engine
73
79
  end
74
80
 
75
81
  class PDFPlugin < Format::Plugin
@@ -98,13 +104,13 @@ module Ruport
98
104
 
99
105
  rendering_options :red_cloth_enabled => true, :erb_enabled => true
100
106
 
101
- renderer :document
107
+ renderer :document
102
108
 
103
109
  renderer :table do
104
110
  rc = data.inject(rendered_field_names) { |s,r|
105
111
  s << "|#{r.to_a.join('|')}|\n"
106
112
  }
107
- Format.document :data => rc, :output_type => :html
113
+ Format.document :data => rc, :plugin => :html
108
114
  end
109
115
 
110
116
  format_field_names do
@@ -23,7 +23,7 @@ class TestBuilder < Test::Unit::TestCase
23
23
  end
24
24
 
25
25
  assert_equal(DataSet.new( %w[ col1 col2 col3 ],
26
- [ %w[ a b c ], %w[ d e f ]]),
26
+ :data => [ %w[ a b c ], %w[ d e f ]]),
27
27
  @builder.render_data_snatcher)
28
28
 
29
29
  end
@@ -33,10 +33,10 @@ class TestDataRow < Test::Unit::TestCase
33
33
  end
34
34
 
35
35
  def test_constructor
36
- row = Ruport::DataRow.new([1,2,3],%w[a b c])
37
- row2 = Ruport::DataRow.new({"a" => 1, "b" => 2, "c" => 3}, %w[a b c])
38
- row3 = Ruport::DataRow.new(row2, %w[ a b c])
39
- row4 = Ruport::DataRow.new(row3, %w[ a b c], :tags => [:awesome, :cool])
36
+ row = Ruport::DataRow.new(%w[a b c], :data => [1,2,3])
37
+ row2 = Ruport::DataRow.new(%w[a b c], :data => {"a" => 1, "b" => 2, "c" => 3})
38
+ row3 = Ruport::DataRow.new(%w[a b c], :data => row2)
39
+ row4 = Ruport::DataRow.new(%w[a b c], {:data => row3, :tags => [:awesome, :cool]})
40
40
 
41
41
  assert_equal(row, row2)
42
42
  assert_equal(row2, row3)
@@ -76,29 +76,29 @@ class TestDataRow < Test::Unit::TestCase
76
76
  end
77
77
 
78
78
  def test_equality
79
- assert( Ruport::DataRow.new([1,2], %w[ a b ]) ==
80
- Ruport::DataRow.new([1,2], %w[ a b ]) )
81
- assert( Ruport::DataRow.new([1,2], %w[ a b ]) !=
82
- Ruport::DataRow.new([1,2], %w[ c d ]) )
83
- a = Ruport::DataRow.new([1,2,3], %w[ a b c ])
79
+ assert( Ruport::DataRow.new(%w[ a b ], :data => [1,2]) ==
80
+ Ruport::DataRow.new(%w[ a b ], :data => [1,2]) )
81
+ assert( Ruport::DataRow.new(%w[ a b ], :data => [1,2]) !=
82
+ Ruport::DataRow.new(%w[ c d ], :data => [1,2]) )
83
+ a = Ruport::DataRow.new(%w[ a b c ], :data => [1,2,3])
84
84
  a.tag_as :apple
85
- b = Ruport::DataRow.new([1,2,3], %w[ a b c ])
85
+ b = Ruport::DataRow.new(%w[ a b c ], :data => [1,2,3])
86
86
  assert( a == b )
87
87
  assert( a.eql?(b) )
88
88
 
89
89
  end
90
90
 
91
91
  def test_addition
92
- row1 = Ruport::DataRow.new [1,2,3], %w[ a b c ]
93
- row2 = Ruport::DataRow.new [4,5,6], %w[ d e f ]
92
+ row1 = Ruport::DataRow.new %w[ a b c ], :data => [1,2,3]
93
+ row2 = Ruport::DataRow.new %w[ d e f ], :data => [4,5,6]
94
94
 
95
- expected = Ruport::DataRow.new [1,2,3,4,5,6], %w[ a b c d e f ]
95
+ expected = Ruport::DataRow.new %w[ a b c d e f ], :data => [1,2,3,4,5,6]
96
96
 
97
97
  assert_equal( expected, row1 + row2 )
98
98
  end
99
99
 
100
100
  def test_clone
101
- row1 = Ruport::DataRow.new [1,2,3], %w[ a b c ]
101
+ row1 = Ruport::DataRow.new %w[ a b c ], :data => [1,2,3]
102
102
  row2 = row1.clone
103
103
 
104
104
  assert( row1.object_id != row2.object_id )
@@ -109,14 +109,14 @@ class TestDataRow < Test::Unit::TestCase
109
109
 
110
110
  #FIXME: add edge cases
111
111
  def test_to_h
112
- row1 = Ruport::DataRow.new [1,2,3], %w[ a b c ]
112
+ row1 = Ruport::DataRow.new %w[ a b c ], :data => [1,2,3]
113
113
  assert_instance_of(Hash,row1.to_h)
114
114
  assert_equal({ "a" => 1, "b" => 2, "c" => 3},row1.to_h)
115
115
  end
116
116
 
117
117
  def test_ensure_arrays_not_modified
118
118
  arr = [1,2,3]
119
- row1 = Ruport::DataRow.new arr, %w[ a b c ]
119
+ row1 = Ruport::DataRow.new %w[ a b c ], :data => arr
120
120
  assert_equal( [1,2,3], arr )
121
121
  end
122
122
 
@@ -11,8 +11,7 @@ class TestDataSet < Test::Unit::TestCase
11
11
  @data = DataSet.new
12
12
  @data.fields = %w[ col1 col2 col3 ]
13
13
  @data.default = ""
14
- @data << %w[ a b c ]
15
- @data << { "col1" => "d", "col3" => "e"}
14
+ @data << %w[ a b c ] << { "col1" => "d", "col3" => "e"}
16
15
  end
17
16
 
18
17
  def test_new
@@ -20,14 +19,14 @@ class TestDataSet < Test::Unit::TestCase
20
19
  my_data = DataSet.new(fields)
21
20
  assert_equal(fields,my_data.fields)
22
21
 
23
- my_filled_data = DataSet.new( fields, [[1,2,3],[4,5,6]] )
22
+ my_filled_data = DataSet.new( fields, :data => [[1,2,3],[4,5,6]] )
24
23
 
25
24
  assert_equal( [[1,2,3],[4,5,6]], my_filled_data.map { |r| r.to_a } )
26
25
 
27
26
  hash_filling = [ { "col1" => 9, "col2" => 6, "col3" => 0 },
28
27
  { "col1" => 54, "col3" => 1 } ]
29
28
 
30
- my_filled_data = DataSet.new(fields,hash_filling)
29
+ my_filled_data = DataSet.new(fields, :data => hash_filling)
31
30
 
32
31
  assert_equal( [[9,6,0],[54,nil,1]], my_filled_data.map { |r| r.to_a } )
33
32
 
@@ -46,6 +45,11 @@ class TestDataSet < Test::Unit::TestCase
46
45
  assert_equal( ['x','x','x'],
47
46
  @data[2].to_a )
48
47
  end
48
+
49
+ def test_delete_if
50
+ @data.delete_if { |r| r.any? { |e| e.empty? } }
51
+ assert_equal([%w[a b c]],@data.to_a)
52
+ end
49
53
 
50
54
  def test_brackets
51
55
  row0 = { "col1" => "a", "col2" => "b", "col3" => "c" }
@@ -77,6 +81,71 @@ class TestDataSet < Test::Unit::TestCase
77
81
  assert(@data.eql?(data2) && data2.eql?(@data))
78
82
  end
79
83
 
84
+ def test_shaped_like?
85
+ a = DataSet.new
86
+ a.fields = %w[ col1 col2 col3 ]
87
+ assert(@data.shaped_like?(a))
88
+ assert(a.shaped_like?(@data))
89
+ end
90
+
91
+ def test_union
92
+ a = DataSet.new
93
+ a.fields = %w[ col1 col2 col3 ]
94
+ a << %w[ a b c ]
95
+ a << %w[ x y z ]
96
+ b = a | @data
97
+ assert_kind_of(DataSet, b)
98
+ assert_equal(b.data.length, 3)
99
+ assert_equal([ %w[a b c], %w[x y z], ["d","","e"] ], b.to_a)
100
+ assert_equal((a | @data), a.union(@data))
101
+ end
102
+
103
+ def test_difference
104
+ a = DataSet.new
105
+ a.fields = %w[ col1 col2 col3 ]
106
+ a << %w[ a b c ]
107
+ a << %w[ x y z ]
108
+ b = a - @data
109
+ assert_kind_of(DataSet, b)
110
+ assert_equal(b.data.length, 1)
111
+ assert_equal([ %w[x y z] ], b.to_a)
112
+ assert_equal((a - @data), a.difference(@data))
113
+ end
114
+
115
+ def test_intersection
116
+ a = DataSet.new
117
+ a.fields = %w[ col1 col2 col3 ]
118
+ a << %w[ a b c ]
119
+ a << %w[ x y z ]
120
+ b = a & @data
121
+ assert_kind_of(DataSet, b)
122
+ assert_equal(b.data.length, 1)
123
+ assert_equal([ %w[a b c] ], b.to_a)
124
+ assert_equal((a & @data), a.intersection(@data))
125
+ end
126
+
127
+ def test_concatenation
128
+ a = DataSet.new
129
+ a.fields = %w[ col1 col2 col3 ]
130
+ a << %w[ x y z ]
131
+ newdata = @data.concat(a)
132
+ assert_equal([ %w[a b c], ["d","","e"], %w[x y z] ], newdata.to_a)
133
+ end
134
+
135
+ def test_append_datarow
136
+ row = DataRow.new(%w[ x y z ], :data => %w[ col1 col2 col3 ])
137
+ @data << row
138
+ assert_equal(@data[2], row)
139
+ end
140
+
141
+ def test_append_datarows
142
+ row = DataRow.new(%w[ x y z ], :data => %w[ col1 col2 col3 ])
143
+ row2 = DataRow.new(%w[ u v w ], :data => %w[ col1, col2, col3 ])
144
+ @data << [row, row2]
145
+ assert_equal(@data[2], row)
146
+ assert_equal(@data[3], row2)
147
+ end
148
+
80
149
  def test_empty?
81
150
  a = DataSet.new
82
151
  a.fields = %w[a b c]
@@ -87,14 +156,20 @@ class TestDataSet < Test::Unit::TestCase
87
156
  assert_equal(false,a.empty?)
88
157
  end
89
158
 
159
+ def test_length
160
+ assert_equal(2, @data.length)
161
+ @data << [1,2,3]
162
+ assert_equal(3, @data.length)
163
+ end
164
+
90
165
  def test_load
91
166
  loaded_data = DataSet.load("test/samples/data.csv")
92
- @data.each_with_index do |row,r_index|
93
- row.each_with_index do |field,f_index|
94
- assert_equal(field,loaded_data[r_index][f_index])
95
- end
167
+ assert_equal(@data,loaded_data)
168
+
169
+ loaded_data = DataSet.load("test/samples/data.csv") do |set,row|
170
+ set << row if row.include? 'b'
96
171
  end
97
- #FIXME: add error edges
172
+ assert_equal([%w[a b c]],loaded_data.to_a)
98
173
  end
99
174
 
100
175
  def test_to_csv
@@ -104,11 +179,11 @@ class TestDataSet < Test::Unit::TestCase
104
179
  end
105
180
 
106
181
  def test_to_html
107
- assert_equal("<table>\n <tr>\n <th>col1</th><th>col2</th>" +
108
- "<th>col3</th>\n </tr>\n" +
109
- " <tr>\n <td>a</td><td>b</td><td>c</td>\n </tr>\n" +
110
- " <tr>\n <td>d</td><td></td><td>e</td>\n </tr>\n" +
111
- "</table>", @data.to_html )
182
+ assert_equal("<table>\n\t\t<tr>\n\t\t\t<th>col1 </th>\n\t\t\t"+
183
+ "<th>col2 </th>\n\t\t\t<th>col3</th>\n\t\t</tr>\n"+
184
+ "\t\t<tr>\n\t\t\t<td>a</td>\n\t\t\t<td>b</td>\n\t\t\t"+
185
+ "<td>c</td>\n\t\t</tr>\n\t\t<tr>\n\t\t\t<td>d</td>\n\t"+
186
+ "\t\t<td>e</td>\n\t\t</tr>\n\t</table>", @data.to_html )
112
187
  end
113
188
 
114
189
  def test_select_columns
@@ -123,6 +198,27 @@ class TestDataSet < Test::Unit::TestCase
123
198
  assert_equal( [["c","a"],["e","d"]],
124
199
  @data.select_columns("col3","col1").map { |r| r.to_a } )
125
200
  end
201
+
202
+ def test_select_columns!
203
+ a = [[1,2],[3,4]].to_ds(%w[a b])
204
+ a.select_columns!(*%w[b a])
205
+
206
+ assert_equal(%w[b a],a.fields)
207
+ assert_equal([[2,1],[4,3]],a.to_a)
208
+
209
+ a.select_columns!('a')
210
+
211
+ assert_equal(%w[a], a.fields)
212
+ assert_equal([[1],[3]],a.to_a)
213
+
214
+ a.select_columns!('a','q')
215
+ assert_equal(%w[a q], a.fields)
216
+ assert_equal([[1,nil],[3,nil]],a.to_a)
217
+
218
+ a[0]['q'] =2
219
+ assert_equal([[1,2],[3,nil]],a.to_a)
220
+
221
+ end
126
222
 
127
223
  def test_as
128
224
  data = DataSet.new
@@ -132,15 +228,16 @@ class TestDataSet < Test::Unit::TestCase
132
228
  assert_equal("col1,col2,col3\na,b,c\nd,e,f\n",
133
229
  data.as(:csv) )
134
230
 
135
- assert_equal("<table>\n <tr>\n <th>col1</th><th>col2</th>" +
136
- "<th>col3</th>\n </tr>\n" +
137
- " <tr>\n <td>a</td><td>b</td><td>c</td>\n </tr>\n" +
138
- " <tr>\n <td>d</td><td>e</td><td>f</td>\n </tr>\n" +
139
- "</table>", data.as(:html) )
231
+ assert_equal("<table>\n\t\t<tr>\n\t\t\t<th>col1 </th>"+
232
+ "\n\t\t\t<th>col2 </th>\n\t\t\t<th>col3</th>"+
233
+ "\n\t\t</tr>\n\t\t<tr>\n\t\t\t<td>a</td>\n\t\t\t"+
234
+ "<td>b</td>\n\t\t\t<td>c</td>\n\t\t</tr>\n\t\t<tr>"+
235
+ "\n\t\t\t<td>d</td>\n\t\t\t<td>e</td>\n\t\t\t<td>f</td>"+
236
+ "\n\t\t</tr>\n\t</table>", data.as(:html) )
140
237
  end
141
238
 
142
239
  def test_sigma
143
- data = Ruport::DataSet.new(%w[x],[[3],[5],[8],[2]])
240
+ data = Ruport::DataSet.new(%w[x], :data => [[3],[5],[8],[2]])
144
241
 
145
242
  sum = data.sigma { |r| r["x"] if (r["x"] % 2).zero? }
146
243
  assert_equal(10, sum)
@@ -164,11 +261,11 @@ class TestDataSet < Test::Unit::TestCase
164
261
  end
165
262
 
166
263
  def test_bracket_equals
167
- expected = DataRow.new(%w[apple banana orange], %w[col1 col2 col3])
264
+ expected = DataRow.new(%w[col1 col2 col3], :data => %w[apple banana orange])
168
265
 
169
266
  raw = [ %w[apple banana orange],
170
267
  { "col1" => "apple", "col2" => "banana", "col3" => "orange" },
171
- DataRow.new(%w[apple banana orange], %w[col1 col2 col3])
268
+ DataRow.new(%w[col1 col2 col3], :data => %w[apple banana orange])
172
269
  ]
173
270
  raw.each do |my_row|
174
271
  @data[1] = my_row
@@ -205,17 +302,17 @@ class TestDataSet < Test::Unit::TestCase
205
302
  [1,2,3].to_ds(%w[foo bar soup])
206
303
  }
207
304
 
208
- assert_equal( DataSet.new(%w[a b], [[1,2],[3,4]]),
305
+ assert_equal( DataSet.new(%w[a b], :data => [[1,2],[3,4]]),
209
306
  [[1,2],[3,4]].to_ds(%w[a b]) )
210
307
 
211
- assert_equal( DataSet.new(%w[a b], [{ "a" => 1 },{ "b" => 2}]),
308
+ assert_equal( DataSet.new(%w[a b], :data => [{ "a" => 1 },{ "b" => 2}]),
212
309
  [{"a" => 1}, {"b" => 2}].to_ds(%w[a b]) )
213
- assert_equal( DataSet.new(%w[a b], [DataRow.new([1,2],%w[a b])]),
214
- [DataRow.new([1,2],%w[a b])].to_ds(%w[a b]) )
310
+ assert_equal( DataSet.new(%w[a b], :data => [DataRow.new(%w[a b], :data => [1,2])]),
311
+ [DataRow.new(%w[a b], :data => [1,2])].to_ds(%w[a b]) )
215
312
 
216
313
  # FIXME: Decide whether this test should pass or fail.
217
- # assert_equal( DataSet.new(%w[a b], [DataRow.new([1,2],%w[a b])]),
218
- # [DataRow.new([1,2],%w[a q])].to_ds(%w[a b]) )
314
+ # assert_equal( DataSet.new(%w[a b], [DataRow.new(%w[a b], [1,2])]),
315
+ # [DataRow.new(%w[a q], [1,2])].to_ds(%w[a b]) )
219
316
 
220
317
  end
221
318
 
@@ -0,0 +1,326 @@
1
+ #!/usr/local/bin/ruby -w
2
+
3
+ require "test/unit"
4
+ require "ruport"
5
+
6
+ class TestDataSet < Test::Unit::TestCase
7
+
8
+ include Ruport
9
+
10
+ def setup
11
+ @data = DataSet.new
12
+ @data.fields = %w[ col1 col2 col3 ]
13
+ @data.default = ""
14
+ @data << %w[ a b c ] << { "col1" => "d", "col3" => "e"}
15
+ end
16
+
17
+ def test_new
18
+ fields = %w[ col1 col2 col3 ]
19
+ my_data = DataSet.new(fields)
20
+ assert_equal(fields,my_data.fields)
21
+
22
+ my_filled_data = DataSet.new( fields, :content => [[1,2,3],[4,5,6]] )
23
+
24
+ assert_equal( [[1,2,3],[4,5,6]], my_filled_data.map { |r| r.to_a } )
25
+
26
+ hash_filling = [ { "col1" => 9, "col2" => 6, "col3" => 0 },
27
+ { "col1" => 54, "col3" => 1 } ]
28
+
29
+ my_filled_data = DataSet.new(fields, :content => hash_filling)
30
+
31
+ assert_equal( [[9,6,0],[54,nil,1]], my_filled_data.map { |r| r.to_a } )
32
+
33
+ cloned_set = @data.clone
34
+
35
+ assert_equal( [ %w[a b c], ["d","","e"] ], cloned_set.map { |r| r.to_a } )
36
+ end
37
+
38
+ def test_fields
39
+ assert_equal(%w[ col1 col2 col3 ], @data.fields )
40
+ end
41
+
42
+ def test_default
43
+ @data.default = "x"
44
+ @data << { }
45
+ assert_equal( ['x','x','x'],
46
+ @data[2].to_a )
47
+ end
48
+
49
+ def test_delete_if
50
+ @data.delete_if { |r| r.any? { |e| e.empty? } }
51
+ assert_equal([%w[a b c]],@data.to_a)
52
+ end
53
+
54
+ def test_brackets
55
+ row0 = { "col1" => "a", "col2" => "b", "col3" => "c" }
56
+ row1 = { "col1" => "d", "col2" => "", "col3" => "e" }
57
+ row0.each do |key,value|
58
+ assert_equal( value, @data[0][key] )
59
+ end
60
+ row1.each do |key,value|
61
+ assert_equal( value, @data[1][key] )
62
+ end
63
+ end
64
+
65
+ def test_eql?
66
+ data2 = DataSet.new
67
+ data2.fields = %w[ col1 col2 col3 ]
68
+ data2.default = ""
69
+ data2 << %w[ a b c ]
70
+ data2 << { "col1" => "d", "col3" => "e" }
71
+
72
+ #FIXME: This looks like some shady discrete math assignment
73
+ assert(@data.eql?(data2) && data2.eql?(@data))
74
+ data2 << [2, 3, 4]
75
+ assert(!( @data.eql?(data2) || data2.eql?(@data) ))
76
+ @data << [2, 3, 4]
77
+ assert(@data.eql?(data2) && data2.eql?(@data))
78
+ @data << [8, 9, 10]
79
+ assert(!( @data.eql?(data2) || data2.eql?(@data) ))
80
+ data2 << [8, 9, 10]
81
+ assert(@data.eql?(data2) && data2.eql?(@data))
82
+ end
83
+
84
+ def test_shaped_like?
85
+ a = DataSet.new
86
+ a.fields = %w[ col1 col2 col3 ]
87
+ assert(@data.shaped_like?(a))
88
+ assert(a.shaped_like?(@data))
89
+ end
90
+
91
+ def test_union
92
+ a = DataSet.new
93
+ a.fields = %w[ col1 col2 col3 ]
94
+ a << %w[ a b c ]
95
+ a << %w[ x y z ]
96
+ b = a | @data
97
+ assert_kind_of(DataSet, b)
98
+ assert_equal(b.data.length, 3)
99
+ assert_equal([ %w[a b c], %w[x y z], ["d","","e"] ], b.to_a)
100
+ assert_equal((a | @data), a.union(@data))
101
+ end
102
+
103
+ def test_difference
104
+ a = DataSet.new
105
+ a.fields = %w[ col1 col2 col3 ]
106
+ a << %w[ a b c ]
107
+ a << %w[ x y z ]
108
+ b = a - @data
109
+ assert_kind_of(DataSet, b)
110
+ assert_equal(b.data.length, 1)
111
+ assert_equal([ %w[x y z] ], b.to_a)
112
+ assert_equal((a - @data), a.difference(@data))
113
+ end
114
+
115
+ def test_intersection
116
+ a = DataSet.new
117
+ a.fields = %w[ col1 col2 col3 ]
118
+ a << %w[ a b c ]
119
+ a << %w[ x y z ]
120
+ b = a & @data
121
+ assert_kind_of(DataSet, b)
122
+ assert_equal(b.data.length, 1)
123
+ assert_equal([ %w[a b c] ], b.to_a)
124
+ assert_equal((a & @data), a.intersection(@data))
125
+ end
126
+
127
+ def test_concatenation
128
+ a = DataSet.new
129
+ a.fields = %w[ col1 col2 col3 ]
130
+ a << %w[ x y z ]
131
+ newdata = @data.concat(a)
132
+ assert_equal([ %w[a b c], ["d","","e"], %w[x y z] ], newdata.to_a)
133
+ end
134
+
135
+ def test_append_datarow
136
+ row = DataRow.new(%w[ x y z ],%w[ col1 col2 col3 ])
137
+ @data << row
138
+ assert_equal(@data[2], row)
139
+ end
140
+
141
+ def test_append_datarows
142
+ row = DataRow.new(%w[ x y z ],%w[ col1 col2 col3 ])
143
+ row2 = DataRow.new(%w[ u v w ], %w[ col1, col2, col3 ])
144
+ @data << [row, row2]
145
+ assert_equal(@data[2], row)
146
+ assert_equal(@data[3], row2)
147
+ end
148
+
149
+ def test_empty?
150
+ a = DataSet.new
151
+ a.fields = %w[a b c]
152
+ assert_equal(true,a.empty?)
153
+ assert_equal(false,@data.empty?)
154
+
155
+ a << [1,2,3]
156
+ assert_equal(false,a.empty?)
157
+ end
158
+
159
+ def test_length
160
+ assert_equal(2, @data.length)
161
+ @data << [1,2,3]
162
+ assert_equal(3, @data.length)
163
+ end
164
+
165
+ def test_load
166
+ loaded_data = DataSet.load("test/samples/data.csv")
167
+ assert_equal(@data,loaded_data)
168
+
169
+ loaded_data = DataSet.load("test/samples/data.csv") do |set,row|
170
+ set << row if row.include? 'b'
171
+ end
172
+ assert_equal([%w[a b c]],loaded_data.to_a)
173
+ end
174
+
175
+ def test_to_csv
176
+ loaded_data = DataSet.load("test/samples/data.csv" )
177
+ csv = loaded_data.to_csv
178
+ assert_equal("col1,col2,col3\na,b,c\nd,\"\",e\n",csv)
179
+ end
180
+
181
+ def test_to_html
182
+ assert_equal("<table>\n\t\t<tr>\n\t\t\t<th>col1 </th>\n\t\t\t"+
183
+ "<th>col2 </th>\n\t\t\t<th>col3</th>\n\t\t</tr>\n"+
184
+ "\t\t<tr>\n\t\t\t<td>a</td>\n\t\t\t<td>b</td>\n\t\t\t"+
185
+ "<td>c</td>\n\t\t</tr>\n\t\t<tr>\n\t\t\t<td>d</td>\n\t"+
186
+ "\t\t<td>e</td>\n\t\t</tr>\n\t</table>", @data.to_html )
187
+ end
188
+
189
+ def test_select_columns
190
+ assert_equal( [["a"],["d"]],
191
+ @data.select_columns("col1").map { |r| r.to_a } )
192
+ assert_equal( [["b"],[""]] ,
193
+ @data.select_columns("col2").map { |r| r.to_a } )
194
+ assert_equal( [["c"],["e"]],
195
+ @data.select_columns("col3").map { |r| r.to_a } )
196
+ assert_equal( [["a","b","c"],["d","","e"]],
197
+ @data.select_columns("col1","col2","col3").map { |r| r.to_a })
198
+ assert_equal( [["c","a"],["e","d"]],
199
+ @data.select_columns("col3","col1").map { |r| r.to_a } )
200
+ end
201
+
202
+ def test_select_columns!
203
+ a = [[1,2],[3,4]].to_ds(%w[a b])
204
+ a.select_columns!(*%w[b a])
205
+
206
+ assert_equal(%w[b a],a.fields)
207
+ assert_equal([[2,1],[4,3]],a.to_a)
208
+
209
+ a.select_columns!('a')
210
+
211
+ assert_equal(%w[a], a.fields)
212
+ assert_equal([[1],[3]],a.to_a)
213
+
214
+ a.select_columns!('a','q')
215
+ assert_equal(%w[a q], a.fields)
216
+ assert_equal([[1,nil],[3,nil]],a.to_a)
217
+
218
+ a[0]['q'] =2
219
+ assert_equal([[1,2],[3,nil]],a.to_a)
220
+
221
+ end
222
+
223
+ def test_as
224
+ data = DataSet.new
225
+ data.fields = %w[ col1 col2 col3]
226
+ data << %w[ a b c]
227
+ data << %w[ d e f]
228
+ assert_equal("col1,col2,col3\na,b,c\nd,e,f\n",
229
+ data.as(:csv) )
230
+
231
+ assert_equal("<table>\n\t\t<tr>\n\t\t\t<th>col1 </th>"+
232
+ "\n\t\t\t<th>col2 </th>\n\t\t\t<th>col3</th>"+
233
+ "\n\t\t</tr>\n\t\t<tr>\n\t\t\t<td>a</td>\n\t\t\t"+
234
+ "<td>b</td>\n\t\t\t<td>c</td>\n\t\t</tr>\n\t\t<tr>"+
235
+ "\n\t\t\t<td>d</td>\n\t\t\t<td>e</td>\n\t\t\t<td>f</td>"+
236
+ "\n\t\t</tr>\n\t</table>", data.as(:html) )
237
+ end
238
+
239
+ def test_sigma
240
+ data = Ruport::DataSet.new(%w[x], :content => [[3],[5],[8],[2]])
241
+
242
+ sum = data.sigma { |r| r["x"] if (r["x"] % 2).zero? }
243
+ assert_equal(10, sum)
244
+
245
+ sum = data.sigma { |r| r["x"] }
246
+ assert_equal(18,sum)
247
+
248
+ #check alias
249
+ sum = data.sum { |r| r["x"] }
250
+ assert_equal(18,sum)
251
+
252
+ end
253
+
254
+ def test_remove_columns
255
+ data = @data.remove_columns("col1","col3")
256
+ assert_equal(["col2"],data.fields)
257
+
258
+ data.remove_columns!("col2")
259
+ assert_equal([],data.fields)
260
+ assert(data.empty?)
261
+ end
262
+
263
+ def test_bracket_equals
264
+ expected = DataRow.new(%w[apple banana orange], %w[col1 col2 col3])
265
+
266
+ raw = [ %w[apple banana orange],
267
+ { "col1" => "apple", "col2" => "banana", "col3" => "orange" },
268
+ DataRow.new(%w[apple banana orange], %w[col1 col2 col3])
269
+ ]
270
+ raw.each do |my_row|
271
+ @data[1] = my_row
272
+ assert_instance_of(DataRow, @data[1])
273
+ assert_equal(expected, @data[1])
274
+ end
275
+
276
+ assert_raise(ArgumentError) { @data[1] = "apple" }
277
+ end
278
+
279
+ def test_clone
280
+ data2 = @data.clone
281
+ assert( @data.object_id != data2.object_id )
282
+ assert_equal( @data, data2 )
283
+ data2 << %w[ f o o ]
284
+ assert( @data != data2 )
285
+ assert( data2 != @data )
286
+ end
287
+
288
+ def test_array_hack
289
+ assert_nothing_raised {
290
+ [ { :a => :b, :c => :d }, { :e => :f, :g => :h } ].to_ds(%w[a e])
291
+ }
292
+ assert_nothing_raised {
293
+ [ [1,2,3], [4,5,6], [7,8,9] ].to_ds(%w[a b c])
294
+ }
295
+ assert_raise(ArgumentError) {
296
+ %w[d e f].to_ds(%w[a b c])
297
+ }
298
+ assert_raise(ArgumentError) {
299
+ [:foo,:bar,:dog].to_ds(%w[tree cat animal])
300
+ }
301
+ assert_raise(ArgumentError) {
302
+ [1,2,3].to_ds(%w[foo bar soup])
303
+ }
304
+
305
+ assert_equal( DataSet.new(%w[a b], :content => [[1,2],[3,4]]),
306
+ [[1,2],[3,4]].to_ds(%w[a b]) )
307
+
308
+ assert_equal( DataSet.new(%w[a b], :content => [{ "a" => 1 },{ "b" => 2}]),
309
+ [{"a" => 1}, {"b" => 2}].to_ds(%w[a b]) )
310
+ assert_equal( DataSet.new(%w[a b], :content => [DataRow.new([1,2],%w[a b])]),
311
+ [DataRow.new([1,2],%w[a b])].to_ds(%w[a b]) )
312
+
313
+ # FIXME: Decide whether this test should pass or fail.
314
+ # assert_equal( DataSet.new(%w[a b], [DataRow.new([1,2],%w[a b])]),
315
+ # [DataRow.new([1,2],%w[a q])].to_ds(%w[a b]) )
316
+
317
+ end
318
+
319
+ def test_append_chain
320
+ data2 = DataSet.new(%w[col1 col2 col3])
321
+ data2.default=""
322
+ data2 << %w[ a b c ] << { "col1" => "d", "col3" => "e" }
323
+ assert_equal @data, data2
324
+ end
325
+
326
+ end
metadata CHANGED
@@ -3,8 +3,8 @@ rubygems_version: 0.8.11
3
3
  specification_version: 1
4
4
  name: ruport
5
5
  version: !ruby/object:Gem::Version
6
- version: 0.4.4
7
- date: 2006-06-06 00:00:00 -04:00
6
+ version: 0.4.5
7
+ date: 2006-06-09 00:00:00 -04:00
8
8
  summary: A generalized Ruby report generation and templating engine.
9
9
  require_paths:
10
10
  - lib
@@ -28,11 +28,11 @@ cert_chain:
28
28
  authors:
29
29
  - Gregory Brown
30
30
  files:
31
+ - examples/fieldless_table.rb
31
32
  - examples/line_plotter.rb
32
33
  - examples/pdf.rb
33
34
  - examples/long.txt
34
35
  - examples/new_plugin.rb
35
- - examples/fieldless_table.rb
36
36
  - lib/ruport
37
37
  - lib/ruport.rb
38
38
  - lib/ruport/query
@@ -53,12 +53,12 @@ files:
53
53
  - lib/ruport/format/plugin.rb
54
54
  - lib/ruport/report/mailer.rb
55
55
  - test/samples
56
+ - test/tc_format_engine.rb
56
57
  - test/tc_element.rb
57
58
  - test/tc_format.rb
58
59
  - test/ts_all.rb
59
60
  - test/tc_data_row.rb
60
61
  - test/tc_ruport.rb
61
- - test/unit.log
62
62
  - test/tc_section.rb
63
63
  - test/tc_database.rb
64
64
  - test/tc_query.rb
@@ -73,7 +73,7 @@ files:
73
73
  - test/tc_state.rb
74
74
  - test/tc_data_set.rb
75
75
  - test/tc_builder.rb
76
- - test/tc_format_engine.rb
76
+ - test/tc_data_set.rb~
77
77
  - test/tc_plugin.rb
78
78
  - test/samples/five_paragraphs.txt
79
79
  - test/samples/ross_report.txt
@@ -1,8 +0,0 @@
1
- # Logfile created on Tue Jun 06 00:16:40 EDT 2006 by logger.rb/1.5.2.7
2
- F, [2006-06-06T00:16:40.836111 #10456] FATAL -- : Missing host for mailer bar
3
- F, [2006-06-06T00:16:40.837386 #10456] FATAL -- : Missing DSN for source foo!
4
- F, [2006-06-06T00:16:40.855495 #10456] FATAL -- : Cannot convert data to DataRow
5
- F, [2006-06-06T00:16:40.855965 #10456] FATAL -- : Cannot convert data to DataRow
6
- F, [2006-06-06T00:16:40.856380 #10456] FATAL -- : Cannot convert data to DataRow
7
- F, [2006-06-06T00:16:40.859864 #10456] FATAL -- : Cannot convert data to DataRow
8
- F, [2006-06-06T00:16:40.915668 #10456] FATAL -- : no block given!