Reputation: 13568
Suppose I am developing a Ruby gem that will be installed in a project by being added to its Gemfile. From my gem, I want to know the directory path to the installer project's root. How can I get that?
Upvotes: 3
Views: 1683
Reputation: 2767
There is no perfect solution to this problem but you could create a fallback based solution that would work in most general cases. If Rails is defined, we use Rails.root
. If Bundler is defined, we use the Bundler.root
but it would only work when the Gemfile is defined at the project root (which is true in most cases). Else fallback to Dir.pwd
def project_root
if defined?(Rails)
return Rails.root
end
if defined?(Bundler)
return Bundler.root
end
Dir.pwd
end
Upvotes: 4
Reputation: 23317
If you're using Rails, use Rails.root
.
If you don't know the 'main project' is Rails... there isn't neccesarily a great way to do it.
Global $0
is the command name that the ruby script was invoked with. But this won't neccesarily include a path. You can try File.expand_path $0
, but there are a very many reasons that would cause this to not give you what you want, including the program may have changed it's "working directory". Dir.pwd
will give you the "current working directory", which may be the directory of the "project" only if the project was invoked from the "project directory" and the code hasn't changed the current working directory.
In general, there's actually no build-in notion of a "project" or "project directory" in ruby -- you can have a ruby script that isn't really part of a project at all, it's just a file living wherever in the file system you want.
I don't think there's a general reliable way to do this, it depends on how "the project" was set up, which of course a gem can't be sure of.
But if you're using Rails, Rails.root
, because Rails has conventions for how it's set up and invoked, and implements the feature Rails.root
in it's startup processes to record the Rails 'project directory'.
Upvotes: 3