diff options
author | David RodrÃguez <deivid.rodriguez@riseup.net> | 2019-09-05 13:00:50 +0200 |
---|---|---|
committer | Nobuyoshi Nakada <nobu@ruby-lang.org> | 2019-09-05 20:00:50 +0900 |
commit | 2a166cfea22b90e39e3fe9bafab6b806ed4813f6 (patch) | |
tree | d08e04f9c8e56e70a959733f50c8ec4903336f4a | |
parent | d9e6315177be2a1264213a1e7cb215312a23384a (diff) | |
download | bundler-2a166cfea22b90e39e3fe9bafab6b806ed4813f6.tar.gz |
Add `File.absolute_path?` (#2198)
In order to check whether a path is absolute or not in a portable way.
[Feature #15868]
-rw-r--r-- | file.c | 20 | ||||
-rw-r--r-- | spec/ruby/core/file/absolute_path_spec.rb | 53 |
2 files changed, 73 insertions, 0 deletions
@@ -4106,6 +4106,25 @@ s_absolute_path(int c, const VALUE * v, VALUE _) return rb_file_s_absolute_path(c, v); } +/* + * call-seq: + * File.absolute_path?(file_name) -> true or false + * + * Returns <code>true</code> if +file_name+ is an absolute path, and + * <code>false</code> otherwise. + * + * File.absolute_path?("c:/foo") #=> false (on Linux), true (on Windows) + */ + +static VALUE +s_absolute_path_p(VALUE klass, VALUE fname) +{ + VALUE path = rb_get_path(fname); + + if (!rb_is_absolute_path(RSTRING_PTR(path))) return Qfalse; + return Qtrue; +} + enum rb_realpath_mode { RB_REALPATH_CHECK, RB_REALPATH_DIR, @@ -6504,6 +6523,7 @@ Init_File(void) rb_define_singleton_method(rb_cFile, "mkfifo", rb_file_s_mkfifo, -1); rb_define_singleton_method(rb_cFile, "expand_path", s_expand_path, -1); rb_define_singleton_method(rb_cFile, "absolute_path", s_absolute_path, -1); + rb_define_singleton_method(rb_cFile, "absolute_path?", s_absolute_path_p, 1); rb_define_singleton_method(rb_cFile, "realpath", rb_file_s_realpath, -1); rb_define_singleton_method(rb_cFile, "realdirpath", rb_file_s_realdirpath, -1); rb_define_singleton_method(rb_cFile, "basename", rb_file_s_basename, -1); diff --git a/spec/ruby/core/file/absolute_path_spec.rb b/spec/ruby/core/file/absolute_path_spec.rb index d6f3f060c7..52839cf1cc 100644 --- a/spec/ruby/core/file/absolute_path_spec.rb +++ b/spec/ruby/core/file/absolute_path_spec.rb @@ -1,5 +1,58 @@ require_relative '../../spec_helper' +ruby_version_is "2.7" do + describe "File.absolute_path?" do + before :each do + @abs = File.expand_path(__FILE__) + end + + it "returns true if it's an absolute pathname" do + File.absolute_path?(@abs).should be_true + end + + it "returns false if it's a relative path" do + File.absolute_path?(File.basename(__FILE__)).should be_false + end + + it "returns false if it's a tricky relative path" do + File.absolute_path?("C:foo\\bar").should be_false + end + + it "does not expand '~' to a home directory." do + File.absolute_path?('~').should be_false + end + + it "does not expand '~user' to a home directory." do + path = File.dirname(@abs) + Dir.chdir(path) do + File.absolute_path?('~user').should be_false + end + end + + it "calls #to_path on its argument" do + mock = mock_to_path(File.expand_path(__FILE__)) + + File.absolute_path?(mock).should be_true + end + + platform_is_not :windows do + it "takes into consideration the platform's root" do + File.absolute_path?("C:\\foo\\bar").should be_false + File.absolute_path?("C:/foo/bar").should be_false + File.absolute_path?("/foo/bar\\baz").should be_true + end + end + + platform_is :windows do + it "takes into consideration the platform path separator(s)" do + File.absolute_path?("C:\\foo\\bar").should be_true + File.absolute_path?("C:/foo/bar").should be_true + File.absolute_path?("/foo/bar\\baz").should be_false + end + end + end +end + describe "File.absolute_path" do before :each do @abs = File.expand_path(__FILE__) |