summaryrefslogtreecommitdiff
path: root/lib/csv.rb
diff options
context:
space:
mode:
authoradamroyjones <10088591+adamroyjones@users.noreply.github.com>2021-11-18 21:20:09 +0000
committerSutou Kouhei <kou@cozmixng.org>2021-12-24 14:35:33 +0900
commitc70dc3cafb29d89d0377677ead346495183db47e (patch)
tree7acd1af5074bd2e78ee0cb54af78e9224034abca /lib/csv.rb
parent47c53af16872d61576184b0d6935fcf531564cc4 (diff)
[ruby/csv] Add handling for ambiguous parsing options (https://github.com/ruby/csv/pull/226)
GitHub: fix GH-225 With Ruby 3.0.2 and csv 3.2.1, the file ```ruby require "csv" File.open("example.tsv", "w") { |f| f.puts("foo\t\tbar") } CSV.read("example.tsv", col_sep: "\t", strip: true) ``` produces the error ``` lib/csv/parser.rb:935:in `parse_quotable_robust': TODO: Meaningful message in line 1. (CSV::MalformedCSVError) ``` However, the CSV in this example is not malformed; instead, ambiguous options were provided to the parser. It is not obvious (to me) whether the string should be parsed as - `["foo\t\tbar"]`, - `["foo", "bar"]`, - `["foo", "", "bar"]`, or - `["foo", nil, "bar"]`. This commit adds code that raises an exception when this situation is encountered. Specifically, it checks if the column separator either ends with or starts with the characters that would be stripped away. This commit also adds unit tests and updates the documentation. https://github.com/ruby/csv/commit/cc317dd42d
Notes
Notes: Merged: https://github.com/ruby/ruby/pull/5336
Diffstat (limited to 'lib/csv.rb')
-rw-r--r--lib/csv.rb13
1 files changed, 7 insertions, 6 deletions
diff --git a/lib/csv.rb b/lib/csv.rb
index 42e99435cb..06a490f34c 100644
--- a/lib/csv.rb
+++ b/lib/csv.rb
@@ -330,6 +330,7 @@ using CSV::MatchP if CSV.const_defined?(:MatchP)
# liberal_parsing: false,
# nil_value: nil,
# empty_value: "",
+# strip: false,
# # For generating.
# write_headers: nil,
# quote_empty: true,
@@ -337,7 +338,6 @@ using CSV::MatchP if CSV.const_defined?(:MatchP)
# write_converters: nil,
# write_nil_value: nil,
# write_empty_value: "",
-# strip: false,
# }
#
# ==== Options for Parsing
@@ -355,8 +355,9 @@ using CSV::MatchP if CSV.const_defined?(:MatchP)
# - +header_converters+: Specifies the header converters to be used.
# - +skip_blanks+: Specifies whether blanks lines are to be ignored.
# - +skip_lines+: Specifies how comments lines are to be recognized.
-# - +strip+: Specifies whether leading and trailing whitespace are
-# to be stripped from fields..
+# - +strip+: Specifies whether leading and trailing whitespace are to be
+# stripped from fields. This must be compatible with +col_sep+; if it is not,
+# then an +ArgumentError+ exception will be raised.
# - +liberal_parsing+: Specifies whether \CSV should attempt to parse
# non-compliant data.
# - +nil_value+: Specifies the object that is to be substituted for each null (no-text) field.
@@ -935,6 +936,7 @@ class CSV
liberal_parsing: false,
nil_value: nil,
empty_value: "",
+ strip: false,
# For generating.
write_headers: nil,
quote_empty: true,
@@ -942,7 +944,6 @@ class CSV
write_converters: nil,
write_nil_value: nil,
write_empty_value: "",
- strip: false,
}.freeze
class << self
@@ -1760,11 +1761,11 @@ class CSV
encoding: nil,
nil_value: nil,
empty_value: "",
+ strip: false,
quote_empty: true,
write_converters: nil,
write_nil_value: nil,
- write_empty_value: "",
- strip: false)
+ write_empty_value: "")
raise ArgumentError.new("Cannot parse nil as CSV") if data.nil?
if data.is_a?(String)