[ruby-trunk - Feature #6587][Open] proposal: adding new methods File.rootname and Pathname#rootname

Issue #6587 has been reported by usa (Usaku NAKAMURA).


Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Open
Priority: Normal
Assignee:
Category:
Target version: 2.0.0

みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、dirname、basename、extname などから類推して、rootname というメソッドを File の特異メソッドおよび
Pathname のメソッドとして追加することを提案します。

: File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。

on Unixen

p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

on Windows

p File.rootname(“/foo/bar.txt”) #=> “” (relative path)
p File.rootname(“bar.txt”) #=> “” (relative path)
p File.rootname(“C:/foo/bar.txt”) #=> “C:/” (normal absolute
path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended form
absolute path)

: Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。

Issue #6587 has been updated by kosaki (Motohiro KOSAKI).

心情的には賛成なんですが。。

例えば ruby 配布物の test/ 以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、
それぞれ異なる処理を書いており、UNC や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは
“//./” で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

このパッチによってこのあたりがどこくらい綺麗に書けるようになるのかが、分かると積極的に賛成しやすいなあ、とか
思います。なにを心配してるかというと正規表現で書いた方が短くかけるなら、意識の高い人以外は誰も移行してくれなくて
賽の河原になるんじゃないかという不安がじゃっかんあったりなかったり


Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Open
Priority: Normal
Assignee:
Category:
Target version: 2.0.0

みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、dirname、basename、extname などから類推して、rootname というメソッドを File の特異メソッドおよび
Pathname のメソッドとして追加することを提案します。

: File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。

on Unixen

p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

on Windows

p File.rootname(“/foo/bar.txt”) #=> “” (relative path)
p File.rootname(“bar.txt”) #=> “” (relative path)
p File.rootname(“C:/foo/bar.txt”) #=> “C:/” (normal absolute
path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended form
absolute path)

: Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。

Issue #6587 has been updated by nobu (Nobuyoshi N.).

Description updated

usa (Usaku NAKAMURA) wrote:

そこで、dirname、basename、extname などから類推して、rootname というメソッドを File の特異メソッドおよび Pathname
のメソッドとして追加することを提案します。

: File.rootname(filename) → String

on Windows

p File.rootname(“/foo/bar.txt”) #=> “” (relative path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)

この2つの例だけ違和感があるのですが、それぞれ “/” と “C:” ではないかという気がしました。

具体的には、現在どういうコードが使われていて、それをどう置き換えることを想定しているのでしょうか。


Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Open
Priority: Normal
Assignee:
Category:
Target version: 2.0.0

=begin
みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、(({dirname}))、(({basename}))、(({extname})) などから類推して、(({rootname}))
というメソッドを (({File})) の特異メソッドおよび (({Pathname})) のメソッドとして追加することを提案します。

— File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。
# on Unixen
p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

 # on Windows
 p File.rootname("/foo/bar.txt")         #=> "" (relative path)
 p File.rootname("bar.txt")              #=> "" (relative path)
 p File.rootname("C:/foo/bar.txt")       #=> "C:/" (normal absolute 

path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended
form absolute path)

— Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。
=end

というコードがありますが、これは File.rootname(Dir.pwd) の一行で書けます。
また、test/fileutils/test_fileutils.rbの177~180行目に

root = have_drive_letter? ? ‘C:/’ : ‘/’

というコードがありますが、root = File.rootname(Dir.pwd) と書けさえすればCドライブが存在するという仮定が不要になります。

わたしは、これで説得されました。名前が rootname()がベストなのか自信がないので(他でroot nameという単語を見たことがないという
意味で)、ruby-coreで他にいい名前のアイデアないー?的なメールを出してくれるなら積極的賛成

Issue #6587 has been updated by usa (Usaku NAKAMURA).

こさきさんとなかださんにまとめて回答。

このパッチによってこのあたりがどこくらい綺麗に書けるようになるのかが、分かると積極的に賛成しやすいなあ、とか

具体的には、現在どういうコードが使われていて、それをどう置き換えることを想定しているのでしょうか。

そうですね、例えばtest/rake/test_rake_directory_task.rbの30~34行目に

drive = Dir.pwd
while drive != File.dirname(drive)
drive = File.dirname(drive)
end
drive = drive[0…-1] if drive[-1] == ?/

というコードがありますが、これは File.rootname(Dir.pwd) の一行で書けます。
また、test/fileutils/test_fileutils.rbの177~180行目に

root = have_drive_letter? ? ‘C:/’ : ‘/’

というコードがありますが、root = File.rootname(Dir.pwd)
と書けさえすればCドライブが存在するという仮定が不要になります。

思います。なにを心配してるかというと正規表現で書いた方が短くかけるなら、意識の高い人以外は誰も移行してくれなくて
賽の河原になるんじゃないかという不安がじゃっかんあったりなかったり

少なくとも、私には正規表現であろうがなんだろうが短く正確に書ける自信はないです。
上のrakeのtestの例のようなものが最も確実ではないかと思っていますが、こう書くことを啓蒙して回る気はしないですね。します?

この2つの例だけ違和感があるのですが、それぞれ “/” と “C:” ではないかという気がしました。

rootじゃないものが取れてもしゃーないと思うので素直に諦めました。

あと、今見直して気付きましたが、

p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC absolute path)
は"//host/share/"になるべきでした。


Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Open
Priority: Normal
Assignee:
Category:
Target version: 2.0.0

=begin
みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、(({dirname}))、(({basename}))、(({extname})) などから類推して、(({rootname}))
というメソッドを (({File})) の特異メソッドおよび (({Pathname})) のメソッドとして追加することを提案します。

— File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。
# on Unixen
p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

 # on Windows
 p File.rootname("/foo/bar.txt")         #=> "" (relative path)
 p File.rootname("bar.txt")              #=> "" (relative path)
 p File.rootname("C:/foo/bar.txt")       #=> "C:/" (normal absolute 

path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended
form absolute path)

— Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。
=end

Issue #6587 has been updated by nobu (Nobuyoshi N.).

Category set to core
Assignee set to usa (Usaku NAKAMURA)

古いパッチを貼ってしまったので、最新版はこちらに置きました。
File.rootname by nobu · Pull Request #130 · ruby/ruby · GitHub

Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Open
Priority: Normal
Assignee: usa (Usaku NAKAMURA)
Category: core
Target version: 2.0.0

=begin
みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、(({dirname}))、(({basename}))、(({extname})) などから類推して、(({rootname}))
というメソッドを (({File})) の特異メソッドおよび (({Pathname})) のメソッドとして追加することを提案します。

— File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。
# on Unixen
p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

 # on Windows
 p File.rootname("/foo/bar.txt")         #=> "" (relative path)
 p File.rootname("bar.txt")              #=> "" (relative path)
 p File.rootname("C:/foo/bar.txt")       #=> "C:/" (normal absolute 

path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended
form absolute path)

— Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。
=end

Issue #6587 has been updated by nobu (Nobuyoshi N.).

File 0001-File.rootname.patch added

とりあえずパッチ置いときます。

Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Open
Priority: Normal
Assignee:
Category:
Target version: 2.0.0

=begin
みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、(({dirname}))、(({basename}))、(({extname})) などから類推して、(({rootname}))
というメソッドを (({File})) の特異メソッドおよび (({Pathname})) のメソッドとして追加することを提案します。

— File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。
# on Unixen
p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

 # on Windows
 p File.rootname("/foo/bar.txt")         #=> "" (relative path)
 p File.rootname("bar.txt")              #=> "" (relative path)
 p File.rootname("C:/foo/bar.txt")       #=> "C:/" (normal absolute 

path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended
form absolute path)

— Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。
=end

Issue #6587 has been updated by usa (Usaku NAKAMURA).

Status changed from Open to Assigned
Assignee changed from usa (Usaku NAKAMURA) to matz (Yukihiro M.)

なぜか私が担当になってましたが、それが通るなら勝手に入れるよ!

というわけでまつもとさんよろしくおねがいします。

Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Assigned
Priority: Normal
Assignee: matz (Yukihiro M.)
Category: core
Target version: 2.0.0

=begin
みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、(({dirname}))、(({basename}))、(({extname})) などから類推して、(({rootname}))
というメソッドを (({File})) の特異メソッドおよび (({Pathname})) のメソッドとして追加することを提案します。

— File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。
# on Unixen
p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

 # on Windows
 p File.rootname("/foo/bar.txt")         #=> "" (relative path)
 p File.rootname("bar.txt")              #=> "" (relative path)
 p File.rootname("C:/foo/bar.txt")       #=> "C:/" (normal absolute 

path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended
form absolute path)

— Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。
=end

Issue #6587 has been updated by matz (Yukihiro M.).

WIndowsって /foo/bar,txt は絶対パスじゃないんですね。
となると、rootnameを作ってもUNIXとWindowsでの互換性の向上にはつながりませんよね。
例としてあげられたコードもWindows専用みたいだし。
では、UNIXでは変な値を返すよりもNotImplementedErrorの方がよかったりしません?

後は、名前は本当に適切なのかという点ですね。
個人的にはWindows専用にdriveなんとかって名前にしたほうが良いように思えますが。


Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Assigned
Priority: Normal
Assignee: matz (Yukihiro M.)
Category: core
Target version: 2.0.0

=begin
みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、(({dirname}))、(({basename}))、(({extname})) などから類推して、(({rootname}))
というメソッドを (({File})) の特異メソッドおよび (({Pathname})) のメソッドとして追加することを提案します。

— File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。
# on Unixen
p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

 # on Windows
 p File.rootname("/foo/bar.txt")         #=> "" (relative path)
 p File.rootname("bar.txt")              #=> "" (relative path)
 p File.rootname("C:/foo/bar.txt")       #=> "C:/" (normal absolute 

path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended
form absolute path)

— Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。
=end

WIndows$B$C$F(B /foo/bar,txt $B$O@dBP%Q%9$8$c$J$$$s$G$9$M!#(B

$B%+%l%s%H%G%#%l%/%H%j$,(B d:/hoge $B$@$H(B d:/foo/bar,txt
$B$KE83+$5$l$F$7$^$$$^$9$+$i$M!#(B
$B!J$$$d!"$^$H$b$H$5$s$b@dBPCN$C$F$k$O$:$@$H;W$&$s$@$1$I!&!&!&!K(B

$B$&!<$s!"$&$=$r8@$C$?5$$,$9$k!#(B

$B$"$?$j$r8+$k$H(BMicrosoft$B$NMQ8l$G$O$3$l$O!V8=:_$N%I%i%$%V$KBP$9$k@dBP%Q%9!W$H$$$&$i$7$$!#!J$J$s$8$c$=$j$c!K(B

$B$?$V$s!“(Broot$B$,J#?t$”$k$s$@$+$i@dBP%Q%9$O%Q%9$N%f%K!<%/@-$rJ]>Z$7$J$/$F$“$?$j$^$($H$$$&E/3X$J$s$G$7$g$&!#?dB,$G$9$,!#$G!”$J$s$H$J$/MQ8l$r(Bwin
port$B$G$O(BMS$B$H9g$o$;$?$[$&$,$$$$$h$&$J5$$,$7$F$A$g$C$H$0$0$C$F$?$s$G$9$,(B

http://hp.vector.co.jp/authors/VA022575/c/path.html

$B$H$+$r8+$k$H(BMS$B$NMQ8l$b%G%?%i%a$H$+=q$$$F$"$C$FG:$_$OA}$9$P$+$j!&!&!&!&(B

2012/7/13 matz (Yukihiro M.) [email protected]:

Issue #6587 has been updated by matz (Yukihiro M.).

WIndows$B$C$F(B /foo/bar,txt $B$O@dBP%Q%9$8$c$J$$$s$G$9$M!#(B

$B%+%l%s%H%G%#%l%/%H%j$,(B d:/hoge $B$@$H(B d:/foo/bar,txt
$B$KE83+$5$l$F$7$^$$$^$9$+$i$M!#(B
$B!J$$$d!"$^$H$b$H$5$s$b@dBPCN$C$F$k$O$:$@$H;W$&$s$@$1$I!&!&!&!K(B

$B$H$J$k$H!"(Brootname$B$r:n$C$F$b(BUNIX$B$H(BWindows$B$G$N8_49@-$N8~>e$K$O$D$J$,$j$^$;$s$h$M!#(B

$BNc$H$7$F$"$2$i$l$?%3!<%I$b(BWindows$B@lMQ$_$?$$$@$7!#(B

$B$G$O!"(BUNIX$B$G$OJQ$JCM$rJV$9$h$j$b(BNotImplementedError$B$NJ}$,$h$+$C$?$j$7$^$;$s!)(B

$B8e$O!"L>A0$OK\Ev$KE,@Z$J$N$+$H$$$&E@$G$9$M!#(B

$B8D?ME*$K$O(BWindows$B@lMQ$K(Bdrive$B$J$s$H$+$C$FL>A0$K$7$?$[$&$,NI$$$h$&$K;W$($^$9$,!#(B

Windows$B@lMQ$K$7$?$[$&$,$$$$$+$I$&$+$OLg304A$J$N$G%3%a%s%H$7$^$;$s$,!"(B
UNC absolute path
$B$H$+$bE}0lE*$K07$($F$$$k$N$,85%W%m%]!<%5%k$NMxE@$@$H;W$C$F$$$k$N$G(B
drive$B$J$s$H$+$H$$$&L>A0$O0lHL2=$,%o%s%i%s%/Mn$A$F$7$^$C$?0u>]$r<u$1$^$9(B

$B$3$s$K$A$O!"$J$+$`$i(B($B$&(B)$B$G$9!#(B

In message “[ruby-dev:45944] [ruby-trunk - Feature #6587] proposal:
adding new methods File.rootname and Pathname#rootname”
on Jul.14,2012 00:16:18, [email protected] wrote:

$B$H$J$k$H!"(Brootname$B$r:n$C$F$b(BUNIX$B$H(BWindows$B$G$N8_49@-$N8~>e$K$O$D$J$,$j$^$;$s$h$M!#(B

$BNc$H$7$F$"$2$i$l$?%3!<%I$b(BWindows$B@lMQ$_$?$$$@$7!#(B

$B$G$O!"(BUNIX$B$G$OJQ$JCM$rJV$9$h$j$b(BNotImplementedError$B$NJ}$,$h$+$C$?$j$7$^$;$s!)(B

“/”
$B$,JQ$JCM$+$I$&$+$h$/$o$+$j$^$;$s$,(B($BJQ$J$N(B?)$B!“3N$+$K8_49@-(B
$B$N8~>e$K7R$,$k$h$&$J%f!<%9%1!<%9$O;W$$$D$-$^$;$s$M$(!#(B
UNIX$BB&$K$”$C$F:$$k$3$H$,$"$k$N$+$I$&$+$O$h$/$o$+$j$^$;$s!#(B

$B8e$O!"L>A0$OK\Ev$KE,@Z$J$N$+$H$$$&E@$G$9$M!#(B

$B8D?ME*$K$O(BWindows$B@lMQ$K(Bdrive$B$J$s$H$+$C$FL>A0$K$7$?$[$&$,NI$$$h$&$K;W$($^$9$,!#(B

$B$3$l$O>.:j$5$s$,8@$C$F$*$i$l$k$h$&$K%I%i%$%V$N$_$r07$&$o$1$8(B
$B$c$J$$$N$G(Bdrive$B$J$s$H$+$O$“$^$j$h$/$J$$$H;W$C$F$$$^$9!#(B
UNIX$B$G@dBP$KITMW$J$i!”(Bwindows_rootname$B$H$+$K$7$^$9$+(B?

$B$=$l$G$O!#(B

$B$^$D$b$H(B $B$f$-$R$m$G$9(B

In message “Re: [ruby-dev:45967] Re: [ruby-trunk - Feature #6587]
proposal: adding new methods File.rootname and Pathname#rootname”
on Tue, 17 Jul 2012 10:37:18 +0900, “U.Nakamura”
[email protected] writes:

|> $BNc$H$7$F$“$2$i$l$?%3!<%I$b(BWindows$B@lMQ$_$?$$$@$7!#(B
|>
$B$G$O!”(BUNIX$B$G$OJQ$JCM$rJV$9$h$j$b(BNotImplementedError$B$NJ}$,$h$+$C$?$j$7$^$;$s!)(B
|
|“/” $B$,JQ$JCM$+$I$&$+$h$/$o$+$j$^$;$s$,(B($BJQ$J$N(B?)$B!“3N$+$K8_49@-(B
|$B$N8~>e$K7R$,$k$h$&$J%f!<%9%1!<%9$O;W$$$D$-$^$;$s$M$(!#(B
|UNIX$BB&$K$”$C$F:$$k$3$H$,$"$k$N$+$I$&$+$O$h$/$o$+$j$^$;$s!#(B

$B:$$k$3$H$O$J$$$G$7$g$&$1$I!"0UL#ITL@$G$9$h$M!#(B

|$B$3$l$O>.:j$5$s$,8@$C$F$*$i$l$k$h$&$K%I%i%$%V$N$_$r07$&$o$1$8(B
|$B$c$J$$$N$G(Bdrive$B$J$s$H$+$O$“$^$j$h$/$J$$$H;W$C$F$$$^$9!#(B
|UNIX$B$G@dBP$KITMW$J$i!”(Bwindows_rootname$B$H$+$K$7$^$9$+(B?

UNC$B$J$s$A$c$i$r07$&(BUNIX$B$G$b0UL#$N$“$k3HD%$H$$$&$N$O$”$j$($k(B
$B$N$+$b$7$l$^$;$s!#CN$i$s$1$I!#(B

$B$$$:$l$K$7$F$b8=:_$NDs0F$O!"L>A0!&5sF0$H$b$K40A4$K$O;?@.$G$-(B
$B$J$$$N$G!"0lEY%j%8%'%/%H$7$^$9!#$b$&$7$A$c$C$?$1$I!#(B

Windows$B@lMQ$K$9$k$+!“HFMQ$N%f!<%9%1!<%9$r$”$2$k$+!"$I$A$i$G$b(B
$B$$$$$1$I!"I,MW$J$i:FDs0F$7$F$/$@$5$$!#(B

                            $B$^$D$b$H(B $B$f$-$R$m(B /:|)

Issue #6587 has been updated by matz (Yukihiro M.).

Status changed from Assigned to Rejected


Feature #6587: proposal: adding new methods File.rootname and
Pathname#rootname

Author: usa (Usaku NAKAMURA)
Status: Rejected
Priority: Normal
Assignee: matz (Yukihiro M.)
Category: core
Target version: 2.0.0

=begin
みんな大好き Unixen ではパスの先頭は ‘/’ で始まるものという暗黙の前提がありますが、Windows ではドライブレターおよび UNC
というものがあるのでその前提が成り立たないことは広く知られていると思います。
Ruby はドライブレターや UNC
はそれなりに適切に取り扱うようになっていますが、残念ながらパス名を処理する際には依然としてロジックを自前で用意する必要があります。
例えば ruby 配布物の test/
以下を見ると、独自にドライブレター周りを扱おうとしているコードが散見されますが、それぞれ異なる処理を書いており、UNC
や拡張パス名(という名前でいいかどうかわかりませんが、“//?/” あるいは “//./”
で始まるもの)まで含めて適切に取り扱えているコードはほぼありません。

そこで、(({dirname}))、(({basename}))、(({extname})) などから類推して、(({rootname}))
というメソッドを (({File})) の特異メソッドおよび (({Pathname})) のメソッドとして追加することを提案します。

— File.rootname(filename) → String
filename のうち、ルートディレクトリあるいはそれに相当する部分を文字列として返します。
filename が相対パスなどの場合は “”(空文字列)を返します。
# on Unixen
p File.rootname(“/foo/bar.txt”) #=> “/” (absolute path)
p File.rootname(“bar.txt”) #=> “” (relative path)

 # on Windows
 p File.rootname("/foo/bar.txt")         #=> "" (relative path)
 p File.rootname("bar.txt")              #=> "" (relative path)
 p File.rootname("C:/foo/bar.txt")       #=> "C:/" (normal absolute 

path)
p File.rootname(“C:bar.txt”) #=> “” (relative path)
p File.rootname(“//host/share/baz.txt”) #=> “//host/share” (UNC
absolute path)
p File.rootname(“//?/C:/foo/bar.txt”) #=> “//?/C:/” (extended
form absolute path)

— Pathname#rootname
Pathname.new(File.rootname(self.to_s)) と同じです。
=end