summaryrefslogtreecommitdiff
path: root/lib/csv.rb
diff options
context:
space:
mode:
authornaruse <naruse@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2009-10-15 18:19:15 +0000
committernaruse <naruse@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2009-10-15 18:19:15 +0000
commite3c75483635634b560de6736af03f121aeb09e68 (patch)
treeb73fc8d1a8752bce06b64f658a556edb408bf603 /lib/csv.rb
parente5e49b3a2797249708eb3fa4754c58f718da50c9 (diff)
* lib/csv.rb (CSV#read_to_char): set encoding and verify data
which read from io before encode it to @encoding. * lib/csv.rb (CSV#raw_encoding): add to get @io's encoding. * lib/csv.rb (CSV#read_io): add to read string and set @io's encoding. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25353 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'lib/csv.rb')
-rw-r--r--lib/csv.rb28
1 files changed, 19 insertions, 9 deletions
diff --git a/lib/csv.rb b/lib/csv.rb
index aae94888cd..8545e661b1 100644
--- a/lib/csv.rb
+++ b/lib/csv.rb
@@ -1550,12 +1550,7 @@ class CSV
# create the IO object we will read from
@io = if data.is_a? String then StringIO.new(data) else data end
# honor the IO encoding if we can, otherwise default to ASCII-8BIT
- @encoding = if @io.respond_to? :internal_encoding
- @io.internal_encoding || @io.external_encoding
- elsif @io.is_a? StringIO
- @io.string.encoding
- end
- @encoding ||= Encoding.default_internal || Encoding.default_external
+ @encoding = raw_encoding || Encoding.default_internal || Encoding.default_external
#
# prepare for building safe regular expressions in the target encoding,
# if we can transcode the needed characters
@@ -1989,7 +1984,6 @@ class CSV
sample = read_to_char(1024)
sample += read_to_char(1) if sample[-1..-1] == encode_str("\r") and
not @io.eof?
-
# try to find a standard separator
if sample =~ encode_re("\r\n?|\n")
@row_sep = $&
@@ -2272,8 +2266,9 @@ class CSV
#
def read_to_char(bytes)
return "" if @io.eof?
- data = @io.read(bytes)
+ data = read_io(bytes)
begin
+ raise unless data.valid_encoding?
encoded = encode_str(data)
raise unless encoded.valid_encoding?
return encoded
@@ -2281,11 +2276,26 @@ class CSV
if @io.eof? or data.size >= bytes + 10
return data
else
- data += @io.read(1)
+ data += read_io(1)
retry
end
end
end
+
+ private
+ def raw_encoding
+ if @io.respond_to? :internal_encoding
+ @io.internal_encoding || @io.external_encoding
+ elsif @io.is_a? StringIO
+ @io.string.encoding
+ else
+ @io.encoding
+ end
+ end
+
+ def read_io(bytes)
+ @io.read(bytes).force_encoding(raw_encoding)
+ end
end
# Another name for CSV::instance().