Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Confusing behavior of File.dirname

Tags:

ruby

I have written a couple of small Ruby scripts for system administration using Ruby 1.9.3. In one script I use:

File.dirname(__FILE__)

to get the directory of the script file. This returns a relative path, however when I call the script from a second script File.dirname returns an absolute path.

Ruby Doc lists an absolute return path in its example whereas I found a discussion on Ruby Forum where a user says dirname should only return a relative path.

I am using the suggested solution from Ruby Forums to use File.expand_path to always get the absolute path like this:

File.expand_path(File.dirname(__FILE__))

but is there a way to make the behaviour of dirname consistent?


UPDATE:

To expand on Janathan Cairs answer, I made two scripts:

s1.rb:

puts "External script __FILE__: #{File.dirname(__FILE__)}"

s0.rb:

puts "Local script __FILE__: #{File.dirname(__FILE__)}"
require './s1.rb'

Running ./s0.rb gives the following output:

Local script __FILE__: .
External script __FILE__: /home/kenneth/Pictures/wp/rip_vault
like image 290
Kenneth Avatar asked Mar 12 '13 10:03

Kenneth


1 Answers

File.dirname should return an absolute path if given an absolute path, and a relative path if given a relative path:

File.dirname('/home/jon/test.rb') # => '/home/jon'
File.dirname('test.rb') # => '.'

__FILE__ returns the name of the current script, which is therefore a relative path from the current directory. That means you should always use expand_path if you want to get the absolute path with File.dirname(__FILE__).

NB Ruby 2.0.0 introduces the __dir__ constant

like image 106
Jon Cairns Avatar answered Oct 11 '22 13:10

Jon Cairns