aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorktsj <ktsj@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2013-09-07 04:34:27 +0000
committerktsj <ktsj@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2013-09-07 04:34:27 +0000
commit0a4801e768cd93c79666f32460306f132009aa9d (patch)
tree41f623a2805d42f52d14e61aaf7f04935b27bb1e
parentdd946739dd5cf4c6e9f6e1d31dfbcccc937e9d4f (diff)
downloadruby-0a4801e768cd93c79666f32460306f132009aa9d.tar.gz
* lib/find.rb (Find.find): respect the encodings of arguments.
[ruby-dev:47530] [Feature #8657] * test/test_find.rb: add tests. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@42866 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r--ChangeLog7
-rw-r--r--lib/find.rb40
-rw-r--r--test/test_find.rb34
3 files changed, 64 insertions, 17 deletions
diff --git a/ChangeLog b/ChangeLog
index d88544ba1c..8b3a82af70 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,10 @@
+Sat Sep 7 13:29:22 2013 Kazuki Tsujimoto <kazuki@callcc.net>
+
+ * lib/find.rb (Find.find): respect the encodings of arguments.
+ [ruby-dev:47530] [Feature #8657]
+
+ * test/test_find.rb: add tests.
+
Sat Sep 7 10:40:32 2013 Tanaka Akira <akr@fsij.org>
* ext/socket/mkconstants.rb (TCP_FASTOPEN): Defined for TCP fast open.
diff --git a/lib/find.rb b/lib/find.rb
index 571609cdef..6f3e4282ed 100644
--- a/lib/find.rb
+++ b/lib/find.rb
@@ -37,30 +37,36 @@ module Find
def find(*paths) # :yield: path
block_given? or return enum_for(__method__, *paths)
- paths.collect!{|d| raise Errno::ENOENT unless File.exist?(d); d.dup}
- while file = paths.shift
- catch(:prune) do
- yield file.dup.taint
- begin
- s = File.lstat(file)
- rescue Errno::ENOENT, Errno::EACCES, Errno::ENOTDIR, Errno::ELOOP, Errno::ENAMETOOLONG
- next
- end
- if s.directory? then
+ fs_encoding = Encoding.find("filesystem")
+
+ paths.collect!{|d| raise Errno::ENOENT unless File.exist?(d); d.dup}.each do |path|
+ enc = path.encoding == Encoding::US_ASCII ? fs_encoding : path.encoding
+ ps = [path]
+ while file = ps.shift
+ catch(:prune) do
+ yield file.dup.taint
begin
- fs = Dir.entries(file)
+ s = File.lstat(file)
rescue Errno::ENOENT, Errno::EACCES, Errno::ENOTDIR, Errno::ELOOP, Errno::ENAMETOOLONG
next
end
- fs.sort!
- fs.reverse_each {|f|
- next if f == "." or f == ".."
- f = File.join(file, f)
- paths.unshift f.untaint
- }
+ if s.directory? then
+ begin
+ fs = Dir.entries(file, encoding: enc)
+ rescue Errno::ENOENT, Errno::EACCES, Errno::ENOTDIR, Errno::ELOOP, Errno::ENAMETOOLONG
+ next
+ end
+ fs.sort!
+ fs.reverse_each {|f|
+ next if f == "." or f == ".."
+ f = File.join(file, f)
+ ps.unshift f.untaint
+ }
+ end
end
end
end
+ nil
end
#
diff --git a/test/test_find.rb b/test/test_find.rb
index f6e7f7a13d..b26debe547 100644
--- a/test/test_find.rb
+++ b/test/test_find.rb
@@ -210,6 +210,40 @@ class TestFind < Test::Unit::TestCase
}
end
+ def test_encoding_ascii
+ Dir.mktmpdir {|d|
+ File.open("#{d}/a", "w"){}
+ Dir.mkdir("#{d}/b")
+ a = []
+ Find.find(d.encode(Encoding::US_ASCII)) {|f| a << f }
+ a.each do |i|
+ assert(Encoding.compatible?(d.encode(Encoding.find('filesystem')), i))
+ end
+ }
+ end
+
+ def test_encoding_non_ascii
+ Dir.mktmpdir {|d|
+ File.open("#{d}/a", "w"){}
+ Dir.mkdir("#{d}/b")
+ euc_jp = Encoding::EUC_JP
+ win_31j = Encoding::Windows_31J
+ utf_8 = Encoding::UTF_8
+ a = []
+ Find.find(d.encode(euc_jp), d.encode(win_31j), d.encode(utf_8)) {|f| a << [f, f.encoding] }
+ assert_equal([[d, euc_jp], ["#{d}/a", euc_jp], ["#{d}/b", euc_jp],
+ [d, win_31j], ["#{d}/a", win_31j], ["#{d}/b", win_31j],
+ [d, utf_8], ["#{d}/a", utf_8], ["#{d}/b", utf_8]],
+ a)
+ if /mswin|mingw/ =~ RUBY_PLATFORM
+ a = []
+ Dir.mkdir("#{d}/\u{2660}")
+ Find.find("#{d}".encode(utf_8)) {|f| a << [f, f.encoding] }
+ assert_equal([[d, utf_8], ["#{d}/a", utf_8], ["#{d}/b", utf_8], ["#{d}/\u{2660}", utf_8]], a)
+ end
+ }
+ end
+
class TestInclude < Test::Unit::TestCase
include Find