rcsv 0.1.1 → 0.2.1
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.
- checksums.yaml +6 -14
- data/.travis.yml +3 -1
- data/Gemfile.lock +1 -1
- data/README.md +6 -0
- data/RELNOTES +10 -0
- data/ext/rcsv/csv.h +1 -1
- data/ext/rcsv/libcsv.c +6 -6
- data/ext/rcsv/rcsv.c +42 -4
- data/lib/rcsv.rb +10 -5
- data/lib/rcsv/version.rb +1 -1
- data/test/test_rcsv.csv +2 -2
- data/test/test_rcsv_parse.rb +26 -5
- data/test/test_rcsv_raw_parse.rb +24 -3
- data/test/test_rcsv_write.rb +23 -7
- metadata +5 -5
checksums.yaml
CHANGED
@@ -1,15 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
metadata.gz: !binary |-
|
9
|
-
ZmZjZjAzY2VlNjU4MTM0ZDBmZWQwY2NiNTZmNWY4NzBjMzdlNTBhMjJhZjQz
|
10
|
-
ODEzNDc3MjM5ZGJjNjE5MTgxMTQ3MjU3ZTU3YmQwZmQwNWZmNWFkMzlkNzZl
|
11
|
-
ZWExNTVmODFjOGJkNGIwNmFlMDI5MDA5OWY1ODBiNjhiMWNlZmU=
|
12
|
-
data.tar.gz: !binary |-
|
13
|
-
YjZhOWIwZjI0OGMwOTg3NjY1MzgxMjMwYTU4NmFkMzQ3MGU2MWZmNTFjY2Q4
|
14
|
-
MGU5MzM3M2EwOWEwNjVkMzllYzgzM2U2OTQwYTA5ZWZiMDVkMjBjZDJjYTIy
|
15
|
-
NzJiYTY1MzYyM2I0MzBkYjc3OTRkYmQwNjMwZDUyNGJkZmI1MWU=
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 0333dfa0687b5fff49a8102ddbea1368a8335919
|
4
|
+
data.tar.gz: 0c9b534944b188a82c7734b30aac28bdf7f38f80
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 06e065ecb4755ec5acb43132b39672331ce4a5b7e52c656739d6e23b896c5930311232f6e1c7fa0b39357df6e41d138dcee9cb33b040c0e536c1f7f450f48f1a
|
7
|
+
data.tar.gz: 9c46cedf27acf68b9248d8e9b2329f5162bb099bd67585f6ddc61d85d784b83e20a644649a8666ad5b57d074a1e015f7d42f1c58013f559b5e84d0495a1d6e44
|
data/.travis.yml
CHANGED
data/Gemfile.lock
CHANGED
data/README.md
CHANGED
@@ -183,3 +183,9 @@ This way it is possible to read from a File directly, with a 20MiB buffer and pa
|
|
183
183
|
3. Commit your changes (`git commit -am 'Added some feature'`)
|
184
184
|
4. Push to the branch (`git push origin my-new-feature`)
|
185
185
|
5. Create new Pull Request
|
186
|
+
|
187
|
+
|
188
|
+
## Credits
|
189
|
+
|
190
|
+
* Maintainer: Arthur Pirogovski @arp
|
191
|
+
* Contributors: Edward Slavich @eslavich
|
data/RELNOTES
CHANGED
@@ -1,3 +1,13 @@
|
|
1
|
+
Version 0.2.1
|
2
|
+
* removed a bunch of deprecation warnings (by Ivan Zarea)
|
3
|
+
* added Ruby 2.1 support for Travis CI
|
4
|
+
* fixed write tests on Ruby 1.8.7
|
5
|
+
|
6
|
+
Version 0.2.0
|
7
|
+
* added support for big integer numbers (by Edward Slavich)
|
8
|
+
* added support for String encodings for MRI 1.9+ (by Edward Slavich)
|
9
|
+
* added support for sprintf hash arguments for experimental writing
|
10
|
+
|
1
11
|
Version 0.1.1
|
2
12
|
* added :not_match filter that skips rows with values listed in that option
|
3
13
|
* eliminated many potential memory leaks related to exception handling
|
data/ext/rcsv/csv.h
CHANGED
@@ -62,7 +62,7 @@ int csv_init(struct csv_parser *p, unsigned char options);
|
|
62
62
|
int csv_fini(struct csv_parser *p, void (*cb1)(void *, size_t, void *), void (*cb2)(int, void *), void *data);
|
63
63
|
void csv_free(struct csv_parser *p);
|
64
64
|
int csv_error(struct csv_parser *p);
|
65
|
-
char * csv_strerror(int error);
|
65
|
+
const char * csv_strerror(int error);
|
66
66
|
size_t csv_parse(struct csv_parser *p, const void *s, size_t len, void (*cb1)(void *, size_t, void *), void (*cb2)(int, void *), void *data);
|
67
67
|
size_t csv_write(void *dest, size_t dest_size, const void *src, size_t src_size);
|
68
68
|
int csv_fwrite(FILE *fp, const void *src, size_t src_size);
|
data/ext/rcsv/libcsv.c
CHANGED
@@ -68,11 +68,11 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
|
68
68
|
|
69
69
|
#define SUBMIT_CHAR(p, c) ((p)->entry_buf[entry_pos++] = (c))
|
70
70
|
|
71
|
-
static char *csv_errors[] = {"success",
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
71
|
+
static const char *csv_errors[] = {"success",
|
72
|
+
"error parsing data while strict checking enabled",
|
73
|
+
"memory exhausted while increasing buffer size",
|
74
|
+
"data size too large",
|
75
|
+
"invalid status code"};
|
76
76
|
|
77
77
|
int
|
78
78
|
csv_error(struct csv_parser *p)
|
@@ -81,7 +81,7 @@ csv_error(struct csv_parser *p)
|
|
81
81
|
return p->status;
|
82
82
|
}
|
83
83
|
|
84
|
-
char *
|
84
|
+
const char *
|
85
85
|
csv_strerror(int status)
|
86
86
|
{
|
87
87
|
/* Return a textual description of status */
|
data/ext/rcsv/rcsv.c
CHANGED
@@ -9,11 +9,42 @@ static VALUE rcsv_parse_error; /* class Rcsv::ParseError << StandardError; end *
|
|
9
9
|
#define RAISE_WITH_LOCATION(row, column, contents, fmt, ...) \
|
10
10
|
rb_raise(rcsv_parse_error, "[%d:%d '%s'] " fmt, (int)(row), (int)(column), (char *)(contents), ##__VA_ARGS__);
|
11
11
|
|
12
|
+
/* String encoding is only available in Ruby 1.9+ */
|
13
|
+
#ifdef HAVE_RUBY_ENCODING_H
|
14
|
+
|
15
|
+
#include <ruby/encoding.h>
|
16
|
+
|
17
|
+
#define RB_ENC_FIND_INDEX(encoding) \
|
18
|
+
rb_enc_find_index(encoding)
|
19
|
+
|
20
|
+
#define ENCODED_STR_NEW(str, length, enc_index) \
|
21
|
+
({ \
|
22
|
+
VALUE _string = rb_str_new(str, length); \
|
23
|
+
if (enc_index != -1) { \
|
24
|
+
rb_enc_associate_index(_string, enc_index); \
|
25
|
+
} \
|
26
|
+
_string; \
|
27
|
+
})
|
28
|
+
|
29
|
+
#else
|
30
|
+
|
31
|
+
#define RB_ENC_FIND_INDEX(encoding) \
|
32
|
+
({ \
|
33
|
+
rb_raise(rcsv_parse_error, "Character encodings are unavailable in your ruby version!"); \
|
34
|
+
-1; \
|
35
|
+
})
|
36
|
+
|
37
|
+
#define ENCODED_STR_NEW(str, length, enc_index) \
|
38
|
+
rb_str_new(str, length)
|
39
|
+
|
40
|
+
#endif
|
41
|
+
|
12
42
|
struct rcsv_metadata {
|
13
43
|
/* Derived from user-specified options */
|
14
44
|
bool row_as_hash; /* Used to return array of hashes rather than array of arrays */
|
15
45
|
bool empty_field_is_nil; /* Do we convert empty fields to nils? */
|
16
46
|
size_t offset_rows; /* Number of rows to skip before parsing */
|
47
|
+
int encoding_index; /* If available, the encoding index of the original input */
|
17
48
|
|
18
49
|
char * row_conversions; /* A pointer to string/array of row conversions char specifiers */
|
19
50
|
VALUE * only_rows; /* A pointer to array of row filters */
|
@@ -72,17 +103,17 @@ void end_of_field_callback(void * field, size_t field_size, void * data) {
|
|
72
103
|
if (meta->empty_field_is_nil || field_str == NULL) {
|
73
104
|
parsed_field = Qnil;
|
74
105
|
} else {
|
75
|
-
parsed_field =
|
106
|
+
parsed_field = ENCODED_STR_NEW("", 0, meta->encoding_index);
|
76
107
|
}
|
77
108
|
}
|
78
109
|
} else {
|
79
110
|
if (meta->current_col < meta->num_row_conversions) {
|
80
111
|
switch (row_conversion){
|
81
112
|
case 's': /* String */
|
82
|
-
parsed_field =
|
113
|
+
parsed_field = ENCODED_STR_NEW(field_str, field_size, meta->encoding_index);
|
83
114
|
break;
|
84
115
|
case 'i': /* Integer */
|
85
|
-
parsed_field =
|
116
|
+
parsed_field = LL2NUM(atoll(field_str));
|
86
117
|
break;
|
87
118
|
case 'f': /* Float */
|
88
119
|
parsed_field = rb_float_new(atof(field_str));
|
@@ -118,7 +149,7 @@ void end_of_field_callback(void * field, size_t field_size, void * data) {
|
|
118
149
|
);
|
119
150
|
}
|
120
151
|
} else { /* No conversion happens */
|
121
|
-
parsed_field =
|
152
|
+
parsed_field = ENCODED_STR_NEW(field_str, field_size, meta->encoding_index); /* field */
|
122
153
|
}
|
123
154
|
}
|
124
155
|
|
@@ -302,6 +333,12 @@ VALUE rcsv_raw_parse(VALUE ensure_container) {
|
|
302
333
|
meta->offset_rows = (size_t)NUM2INT(option);
|
303
334
|
}
|
304
335
|
|
336
|
+
/* Specify the character encoding of the input data */
|
337
|
+
option = rb_hash_aref(options, ID2SYM(rb_intern("output_encoding")));
|
338
|
+
if (option && (option != Qnil)) {
|
339
|
+
meta->encoding_index = RB_ENC_FIND_INDEX(StringValueCStr(option));
|
340
|
+
}
|
341
|
+
|
305
342
|
/* :only_rows is a list of values where row is only parsed
|
306
343
|
if its fields match those in the passed array.
|
307
344
|
[nil, nil, ["ABC", nil, 1]] skips all rows where 3rd column isn't equal to "ABC", nil or 1 */
|
@@ -421,6 +458,7 @@ static VALUE rb_rcsv_raw_parse(int argc, VALUE * argv, VALUE self) {
|
|
421
458
|
meta.row_as_hash = false;
|
422
459
|
meta.empty_field_is_nil = false;
|
423
460
|
meta.skip_current_row = false;
|
461
|
+
meta.encoding_index = -1;
|
424
462
|
meta.num_columns = 0;
|
425
463
|
meta.current_col = 0;
|
426
464
|
meta.current_row = 0;
|
data/lib/rcsv.rb
CHANGED
@@ -37,22 +37,26 @@ class Rcsv
|
|
37
37
|
|
38
38
|
if csv_data.is_a?(String)
|
39
39
|
csv_data = StringIO.new(csv_data)
|
40
|
-
elsif !(csv_data.respond_to?(:
|
40
|
+
elsif !(csv_data.respond_to?(:each_line) && csv_data.respond_to?(:read))
|
41
41
|
inspected_csv_data = csv_data.inspect
|
42
42
|
raise ParseError.new("Supplied CSV object #{inspected_csv_data[0..127]}#{inspected_csv_data.size > 128 ? '...' : ''} is neither String nor looks like IO object.")
|
43
43
|
end
|
44
44
|
|
45
|
+
if csv_data.respond_to?(:external_encoding)
|
46
|
+
raw_options[:output_encoding] = csv_data.external_encoding.to_s
|
47
|
+
end
|
48
|
+
|
45
49
|
initial_position = csv_data.pos
|
46
50
|
|
47
51
|
case options[:header]
|
48
52
|
when :use
|
49
|
-
header = self.raw_parse(StringIO.new(csv_data.
|
53
|
+
header = self.raw_parse(StringIO.new(csv_data.each_line.first), raw_options).first
|
50
54
|
raw_options[:offset_rows] += 1
|
51
55
|
when :skip
|
52
|
-
header = (0..(csv_data.
|
56
|
+
header = (0..(csv_data.each_line.first.split(raw_options[:col_sep]).count)).to_a
|
53
57
|
raw_options[:offset_rows] += 1
|
54
58
|
when :none
|
55
|
-
header = (0..(csv_data.
|
59
|
+
header = (0..(csv_data.each_line.first.split(raw_options[:col_sep]).count)).to_a
|
56
60
|
end
|
57
61
|
|
58
62
|
raw_options[:row_as_hash] = options[:row_as_hash] # Setting after header parsing
|
@@ -175,7 +179,8 @@ class Rcsv
|
|
175
179
|
field.strftime(format)
|
176
180
|
when :printf
|
177
181
|
format = column_options[:format] || "%s"
|
178
|
-
|
182
|
+
printf_options = column_options[:printf_options]
|
183
|
+
printf_options ? sprintf(format, printf_options.merge(:field => field)) : sprintf(format, field)
|
179
184
|
when :boolean
|
180
185
|
BOOLEAN_FALSE.include?(field.respond_to?(:downcase) ? field.downcase : field) ? 'false' : 'true'
|
181
186
|
else
|
data/lib/rcsv/version.rb
CHANGED
data/test/test_rcsv.csv
CHANGED
@@ -1,5 +1,5 @@
|
|
1
|
-
DSAdsfksjh,iii ooo iii,EDADEDADEDADEDADEDADEDAD,111 333 555,NMLKTF,---==---,//,###,0000000000,Asdad bvd qwert,;sd,@@@,OCTZ,$$$908080, ,true/false
|
2
|
-
C85A5B9F,
|
1
|
+
DSAdsfksjh,iii ooo iii,EDADEDADEDADEDADEDADEDAD,111 333 555,NMLKTF,---==---,//,###,0000000000,Asdad bvd qwert,;'''sd,@@@,OCTZ,$$$908080, """",true/false
|
2
|
+
C85A5B9F,852596378467291748,,96,6838,1983-06-14,"""""C4CA-=; **1679; .. 79","210,11",908e,1281-03-09,7257.4654049904275,20efe749-50fe-4b6a-a603-7f9cd1dc6c6d,3,"New York, NY",u,2.228169203286535,t
|
3
3
|
3ABC8DF7,83229030,,79,9134,1987-05-24,"""""8F14-=; **C9F0; .. 74","321,42",b896,1358-04-08,-139.10142026231654,3e18cc6f-8ef0-41ac-bd4c-79a0120f65fd,8,"San Jose, CA",,-9.549296585513721,1
|
4
4
|
F0A83489,69118080,,73,7008,2016-10-03,"""""C81E-=; **ECCB; .. 89","130,86",a3eb,1341-04-10,7612.699237971538,5b5e3fce-2ea5-4ca9-9749-90fd6dc8dd66,9,"Los Angeles, CA",e,6.047887837492023,f
|
5
5
|
88C6136F,39724702,,59,8417,2015-12-22,"""""C4CA-=; **A87F; .. 89","911,93",1759,1303-01-19,4706.529977113529,0c95197a-bb77-4954-854b-accb3a2c5db6,2,"Los Angeles, CA",z,0.954929658551372,0
|
data/test/test_rcsv_parse.rb
CHANGED
@@ -14,7 +14,7 @@ class RcsvParseTest < Test::Unit::TestCase
|
|
14
14
|
end
|
15
15
|
|
16
16
|
def test_rcsv_parse_unknown_rows
|
17
|
-
csv = "a,b,c,d,e\n1,2,3,4,5"
|
17
|
+
csv = "a,b,c,d,e,f\n1,2,3,4,5,161226289488"
|
18
18
|
parsed_data = Rcsv.parse(csv,
|
19
19
|
:row_as_hash => true,
|
20
20
|
:columns => {
|
@@ -24,6 +24,9 @@ class RcsvParseTest < Test::Unit::TestCase
|
|
24
24
|
},
|
25
25
|
'd' => {
|
26
26
|
:type => :int
|
27
|
+
},
|
28
|
+
'f' => {
|
29
|
+
:type => :int
|
27
30
|
}
|
28
31
|
}
|
29
32
|
)
|
@@ -33,7 +36,8 @@ class RcsvParseTest < Test::Unit::TestCase
|
|
33
36
|
'B' => 2,
|
34
37
|
'c' => '3',
|
35
38
|
'd' => 4,
|
36
|
-
'e' => '5'
|
39
|
+
'e' => '5',
|
40
|
+
'f' => 161226289488,
|
37
41
|
}, parsed_data.first)
|
38
42
|
end
|
39
43
|
|
@@ -57,7 +61,7 @@ class RcsvParseTest < Test::Unit::TestCase
|
|
57
61
|
end
|
58
62
|
|
59
63
|
def test_rcsv_parse_only_rows_not_match
|
60
|
-
csv = "a,1,t\nb,2,false\nc,3,0"
|
64
|
+
csv = "a,1,t,8\nb,2,false,10000000000\nc,3,0,99999999999999\nd,14,false,161226289488"
|
61
65
|
parsed_data = Rcsv.parse(csv,
|
62
66
|
:header => :none,
|
63
67
|
:columns => [
|
@@ -70,10 +74,27 @@ class RcsvParseTest < Test::Unit::TestCase
|
|
70
74
|
{
|
71
75
|
:not_match => true,
|
72
76
|
:type => :bool
|
73
|
-
}
|
77
|
+
},
|
78
|
+
{
|
79
|
+
:not_match => 161226289488,
|
80
|
+
:type => :int
|
81
|
+
},
|
74
82
|
]
|
75
83
|
)
|
76
84
|
|
77
|
-
assert_equal([["b", 2, false], ["c", 3, false]], parsed_data)
|
85
|
+
assert_equal([["b", 2, false, 10000000000], ["c", 3, false, 99999999999999]], parsed_data)
|
86
|
+
end
|
87
|
+
|
88
|
+
if String.instance_methods.include?(:encoding)
|
89
|
+
def test_rcsv_parse_encoding
|
90
|
+
utf8_csv = "a,b,c".force_encoding("UTF-8")
|
91
|
+
ascii_csv = "a,b,c".force_encoding("ASCII-8BIT")
|
92
|
+
|
93
|
+
parsed_utf8_data = Rcsv.parse(utf8_csv, :header => :none)
|
94
|
+
parsed_ascii_data = Rcsv.parse(ascii_csv, :header => :none)
|
95
|
+
|
96
|
+
assert_equal(parsed_utf8_data.first.first.encoding, Encoding::UTF_8)
|
97
|
+
assert_equal(parsed_ascii_data.first.first.encoding, Encoding::ASCII_8BIT)
|
98
|
+
end
|
78
99
|
end
|
79
100
|
end
|
data/test/test_rcsv_raw_parse.rb
CHANGED
@@ -32,7 +32,27 @@ class RcsvRawParseTest < Test::Unit::TestCase
|
|
32
32
|
assert_equal('""C81E-=; **ECCB; .. 89', raw_parsed_tsv_data[3][6])
|
33
33
|
assert_equal("Dallas\t TX", raw_parsed_tsv_data[888][13])
|
34
34
|
end
|
35
|
+
|
36
|
+
if String.instance_methods.include?(:encoding)
|
37
|
+
def test_rcsv_output_encoding_default
|
38
|
+
raw_parsed_csv_data = Rcsv.raw_parse(@csv_data)
|
39
|
+
|
40
|
+
assert_equal(raw_parsed_csv_data[0][2].encoding, Encoding::ASCII_8BIT)
|
41
|
+
end
|
35
42
|
|
43
|
+
def test_rcsv_output_encoding_utf8
|
44
|
+
raw_parsed_csv_data = Rcsv.raw_parse(@csv_data, :output_encoding => "UTF-8")
|
45
|
+
|
46
|
+
assert_equal(raw_parsed_csv_data[0][2].encoding, Encoding::UTF_8)
|
47
|
+
end
|
48
|
+
else
|
49
|
+
def test_rcsv_encoding_unavailable
|
50
|
+
assert_raise Rcsv::ParseError do
|
51
|
+
Rcsv.raw_parse(@csv_data, :output_encoding => "UTF-8")
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
36
56
|
def test_buffer_size
|
37
57
|
raw_parsed_csv_data = Rcsv.raw_parse(@csv_data, :buffer_size => 10)
|
38
58
|
|
@@ -64,7 +84,7 @@ class RcsvRawParseTest < Test::Unit::TestCase
|
|
64
84
|
broken_data = StringIO.new(@csv_data.read.sub(/"/, ''))
|
65
85
|
|
66
86
|
raw_parsed_csv_data = Rcsv.raw_parse(broken_data, :nostrict => true)
|
67
|
-
assert_equal(["DSAdsfksjh", "iii ooo iii", "EDADEDADEDADEDADEDADEDAD", "111 333 555", "NMLKTF", "---==---", "//", "###", "0000000000", "Asdad bvd qwert", ";'''sd", "@@@", "OCTZ", "$$$908080", "\",true/false\nC85A5B9F,
|
87
|
+
assert_equal(["DSAdsfksjh", "iii ooo iii", "EDADEDADEDADEDADEDADEDAD", "111 333 555", "NMLKTF", "---==---", "//", "###", "0000000000", "Asdad bvd qwert", ";'''sd", "@@@", "OCTZ", "$$$908080", "\",true/false\nC85A5B9F,852596378467291748,,96,6838,1983-06-14,\"\"\"C4CA-=; **1679; .. 79", "210,11", "908e", "1281-03-09", "7257.4654049904275", "20efe749-50fe-4b6a-a603-7f9cd1dc6c6d", "3", "New York, NY", "u", "2.228169203286535", "t"], raw_parsed_csv_data.first)
|
68
88
|
end
|
69
89
|
|
70
90
|
def test_only_rows
|
@@ -115,6 +135,7 @@ class RcsvRawParseTest < Test::Unit::TestCase
|
|
115
135
|
|
116
136
|
assert_equal(nil, raw_parsed_csv_data[0][2])
|
117
137
|
assert_equal(96, raw_parsed_csv_data[0][3])
|
138
|
+
assert_equal(852596378467291748, raw_parsed_csv_data[0][1])
|
118
139
|
assert_equal('908e', raw_parsed_csv_data[0][8])
|
119
140
|
assert_equal(-9.549296585513721, raw_parsed_csv_data[1][15])
|
120
141
|
assert_equal('2015-12-22', raw_parsed_csv_data[3][5])
|
@@ -162,7 +183,7 @@ class RcsvRawParseTest < Test::Unit::TestCase
|
|
162
183
|
|
163
184
|
assert_equal({
|
164
185
|
'DSAdsfksjh' => 'C85A5B9F',
|
165
|
-
'iii ooo iii' => '
|
186
|
+
'iii ooo iii' => '852596378467291748',
|
166
187
|
'EDADEDADEDADEDADEDADEDAD' => nil,
|
167
188
|
'111 333 555' => '96',
|
168
189
|
'NMLKTF' => '6838',
|
@@ -226,7 +247,7 @@ class RcsvRawParseTest < Test::Unit::TestCase
|
|
226
247
|
assert_equal(nil, result)
|
227
248
|
assert_equal({
|
228
249
|
'DSAdsfksjh' => 'C85A5B9F',
|
229
|
-
'iii ooo iii' => '
|
250
|
+
'iii ooo iii' => '852596378467291748',
|
230
251
|
'EDADEDADEDADEDADEDADEDAD' => nil,
|
231
252
|
'111 333 555' => '96',
|
232
253
|
'NMLKTF' => '6838',
|
data/test/test_rcsv_write.rb
CHANGED
@@ -4,6 +4,21 @@ require 'date'
|
|
4
4
|
|
5
5
|
class RcsvWriteTest < Test::Unit::TestCase
|
6
6
|
def setup
|
7
|
+
hashformat = if RUBY_VERSION >= '1.9'
|
8
|
+
{
|
9
|
+
:name => 'Hashformat',
|
10
|
+
:formatter => :printf,
|
11
|
+
:format => '%{currency_symbol}%<field>2.2f%{nilly}',
|
12
|
+
:printf_options => {:currency_symbol => '$', :nilly => nil}
|
13
|
+
}
|
14
|
+
else # Ruby before 1.9 didn't support Hash formatting for sprintf()
|
15
|
+
{
|
16
|
+
:name => 'Hashformat',
|
17
|
+
:formatter => :printf,
|
18
|
+
:format => '$%2.2f'
|
19
|
+
}
|
20
|
+
end
|
21
|
+
|
7
22
|
@options = {
|
8
23
|
:header => true,
|
9
24
|
:columns => [
|
@@ -23,6 +38,7 @@ class RcsvWriteTest < Test::Unit::TestCase
|
|
23
38
|
{
|
24
39
|
:name => 'Banana IDDQD'
|
25
40
|
},
|
41
|
+
hashformat,
|
26
42
|
{
|
27
43
|
:name => nil,
|
28
44
|
:formatter => :boolean
|
@@ -31,9 +47,9 @@ class RcsvWriteTest < Test::Unit::TestCase
|
|
31
47
|
}
|
32
48
|
|
33
49
|
@data = [
|
34
|
-
[1, Date.parse('2012-11-11'), 100.234, true, nil],
|
35
|
-
[nil, Date.parse('1970-01-02'), -0.1, :nyancat, 0],
|
36
|
-
[3, Date.parse('2012-12-12'), 0, 'sepulka', 'zoop']
|
50
|
+
[1, Date.parse('2012-11-11'), 100.234, true, 1, nil],
|
51
|
+
[nil, Date.parse('1970-01-02'), -0.1, :nyancat, 123.8891, 0],
|
52
|
+
[3, Date.parse('2012-12-12'), 0, 'sepulka', -122, 'zoop']
|
37
53
|
]
|
38
54
|
|
39
55
|
@writer = Rcsv.new(@options)
|
@@ -41,12 +57,12 @@ class RcsvWriteTest < Test::Unit::TestCase
|
|
41
57
|
|
42
58
|
def test_rcsv_generate_header
|
43
59
|
assert_equal(
|
44
|
-
"ID,Date,Money,Banana IDDQD,\r\n", @writer.generate_header
|
60
|
+
"ID,Date,Money,Banana IDDQD,Hashformat,\r\n", @writer.generate_header
|
45
61
|
)
|
46
62
|
end
|
47
63
|
|
48
64
|
def test_rscv_generate_row
|
49
|
-
assert_equal("1,2012-11-11,$100.23,true,false\r\n", @writer.generate_row(@data.first))
|
65
|
+
assert_equal("1,2012-11-11,$100.23,true,$1.00,false\r\n", @writer.generate_row(@data.first))
|
50
66
|
end
|
51
67
|
|
52
68
|
def test_rcsv_write
|
@@ -59,7 +75,7 @@ class RcsvWriteTest < Test::Unit::TestCase
|
|
59
75
|
io.rewind
|
60
76
|
|
61
77
|
assert_equal(
|
62
|
-
"ID,Date,Money,Banana IDDQD,\r\n1,2012-11-11,$100.23,true,false\r\n,1970-01-02,$-0.10,nyancat,false\r\n3,2012-12-12,$0.00,sepulka,true\r\n", io.read
|
78
|
+
"ID,Date,Money,Banana IDDQD,Hashformat,\r\n1,2012-11-11,$100.23,true,$1.00,false\r\n,1970-01-02,$-0.10,nyancat,$123.89,false\r\n3,2012-12-12,$0.00,sepulka,$-122.00,true\r\n", io.read
|
63
79
|
)
|
64
80
|
end
|
65
81
|
|
@@ -74,7 +90,7 @@ class RcsvWriteTest < Test::Unit::TestCase
|
|
74
90
|
io.rewind
|
75
91
|
|
76
92
|
assert_equal(
|
77
|
-
"1,2012-11-11,$100.23,true,false\r\n,1970-01-02,$-0.10,nyancat,false\r\n3,2012-12-12,$0.00,sepulka,true\r\n", io.read
|
93
|
+
"1,2012-11-11,$100.23,true,$1.00,false\r\n,1970-01-02,$-0.10,nyancat,$123.89,false\r\n3,2012-12-12,$0.00,sepulka,$-122.00,true\r\n", io.read
|
78
94
|
)
|
79
95
|
end
|
80
96
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rcsv
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Arthur Pirogovski
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2014-06-06 00:00:00.000000000 Z
|
12
12
|
dependencies: []
|
13
13
|
description: A libcsv-based CSV parser for Ruby
|
14
14
|
email:
|
@@ -51,17 +51,17 @@ require_paths:
|
|
51
51
|
- ext
|
52
52
|
required_ruby_version: !ruby/object:Gem::Requirement
|
53
53
|
requirements:
|
54
|
-
- -
|
54
|
+
- - '>='
|
55
55
|
- !ruby/object:Gem::Version
|
56
56
|
version: '0'
|
57
57
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
58
58
|
requirements:
|
59
|
-
- -
|
59
|
+
- - '>='
|
60
60
|
- !ruby/object:Gem::Version
|
61
61
|
version: '0'
|
62
62
|
requirements: []
|
63
63
|
rubyforge_project:
|
64
|
-
rubygems_version: 2.
|
64
|
+
rubygems_version: 2.2.2
|
65
65
|
signing_key:
|
66
66
|
specification_version: 4
|
67
67
|
summary: Fast CSV parsing library for MRI based on libcsv. Supports type conversion,
|