Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

whereami gets confused in a Dir.chdir block #1220

Open
dtenenba opened this issue May 4, 2014 · 14 comments · May be fixed by #2312
Open

whereami gets confused in a Dir.chdir block #1220

dtenenba opened this issue May 4, 2014 · 14 comments · May be fixed by #2312

Comments

@dtenenba
Copy link

dtenenba commented May 4, 2014

Hello, I have the following script foo.rb:

require 'tmpdir'
require 'pry'

tmpdir = Dir.mktmpdir

Dir.chdir tmpdir do
     puts "type whereami now"
     binding.pry
end

If I run it like this:

ruby foo.rb

Then when I get dropped into pry I type 'whereami' and see:

[1] pry(main)> whereami
Error: Cannot open "/private/var/folders/jz/_76qjszd4db7drk0sm2vfn5h0000gn/T/d20140504-37098-1vehyq/foo.rb" for reading.

Is there any way around that? Can whereami work off the directory it was in when the script was invoked, not the one it's in when binding.pry is invoked?

I also use pry as a debugger with pry-nav, and experience the same problem when I step into a Dir.chdir block.

@dtenenba
Copy link
Author

dtenenba commented May 5, 2014

What makes you think it is an OS filesystem permissions problem?

To me the problem seems pretty straightforward: whereami looks in the current directory and expects to find my script (foo.rb) but Dir.chdir has changed the directory on us so it doesn't find it.

I had a problem trying to install pry-rescue so I couldn't try that right away.

However, there isn't necessarily an exception or permission error, I just want to go to a certain line of code and look around.

Since I use Dir.chdir blocks extensively this almost seems like a deal-breaker. Really hope it can be fixed because I'd like to continue to reap the benefits of pry. Thanks.

@dtenenba
Copy link
Author

dtenenba commented May 5, 2014

It can't open the file because it doesn't exist.

I can work around the problem by copying the script to the temp directory, like this:

dante@viper:~/tmp$ ruby foo.rb
type whereami now
[1] pry(main)> .cp ~/tmp/foo.rb .
[2] pry(main)> whereami

From: /private/var/folders/jz/_76qjszd4db7drk0sm2vfn5h0000gn/T/d20140504-39877-cy9in6/foo.rb @ line 9 :

     4: tmpdir = Dir.mktmpdir
     5: 
     6: 
     7: Dir.chdir tmpdir do
     8:      puts "type whereami now"
 =>  9:      binding.pry
    10: end

But that's not really a satisfactory workaround for me. THanks.

@dtenenba
Copy link
Author

dtenenba commented May 5, 2014

Hi Johnny,

I'm not trying to be difficult here, but try and imagine why this is not a satisfactory workaround for me.

Since most of my code is in Dir.chdir blocks, this issue means that EVERY TIME I want to use pry and whereami (and next and step from pry-nav) I have to remember what my current directory is, and the directory where the script is, and copy the file.

Then when I'm done I have to remove the file because its presence will cause unintended side effects (my code only expects certain files to be in certain directories).

I wish I was familiar enough with the pry code to offer you a pull request, but it does seem that the problem is pretty easy to fix. When pry starts, you store the directory of the script it's running, accessible with File.dirname(__FILE__). Then use that as the directory to be consulted when the user types whereami.

If I have some time I might try and fix it but I might cause more problems than I solve. ;)

@rondale-sc
Copy link
Contributor

Looked into this a bit. Short of watching the Dir#chdir method and storing a variable that contains the old path I'm not sure how this could be handled.

It looks like when a block is given to Dir#chdir in C-land it stores old path in a struct:

https://github.com/ruby/ruby/blob/trunk/dir.c#L781

Then ensures that the current working directory gets set back to this.

https://github.com/ruby/ruby/blob/trunk/dir.c#L878

Unfortunately, I couldn't find a way to grab that value. Thought of using a method watcher like mwoods79/bubot to store a var to old path and reference it in whereami#setup. But that seems pretty heavy handed, and there might be side effects that I haven't thought of.

Anyways, my two cents. :))))

@dtenenba
Copy link
Author

dtenenba commented May 5, 2014

I don't see why you need to watch Dir#chdir. How about just always examining source code files relative to File.dirname(__FILE__) instead of to the current directory?

@rondale-sc
Copy link
Contributor

@dtenenba If you execute File.dirname(__FILE__) from within the context of the whereami setup method you get "." which unfortunately doesn't resolve the issue.

And if you try to expand the path it ends up using the current working directory, which in this case is inside a tmp directory. And the file doesn't exist there.

@dtenenba
Copy link
Author

dtenenba commented May 5, 2014

@rondale-sc, I see the problem.

That's too bad. I found another workaround that is slightly less annoying, and that is to add another binding.pry before my Dir.chdir block. Then when I hit that first one, I just press control-D and then I'm in the Dir.chdir block but whereami works just fine.

It's still technically an issue but I don't know if it can be fixed. So I'll leave it up to someone else to close this or not. Seems that Dir.chdir should maintain a stack somewhere that can be accessed programmatically. At least I wish it did.

@rondale-sc
Copy link
Contributor

@dtenenba Would be great if you could access the old path. I did think about keeping a stack internal to Pry that'd store the dir value and push the new path each time the directory changed. But that seems pretty unwieldy.

Anyways, good luck. Sorry I couldn't help out here. :)

@envygeeks
Copy link
Contributor

This is definitely an issue that keeps plaguing us when debugging our builders.

@Sod-Almighty
Copy link

I'm still getting this issue three years after it was first reported. Any movement on this?

@epitron
Copy link
Member

epitron commented Apr 17, 2017

The culprit looks like this call to expand_path: https://github.com/pry/pry/blob/master/lib/pry/commands/whereami.rb#L41

If you remove the expand_path call, whereami works again.

I'm not sure why we need to expand the path -- __FILE__ is already expanded on my machine.

Thoughts?

@envygeeks
Copy link
Contributor

envygeeks commented Apr 17, 2017

@epitron Ruby 1.9 now there is __dir__ but that will still break no? I think this might actually be a Ruby bug perhaps?

@epitron
Copy link
Member

epitron commented Apr 17, 2017

Oh, so Ruby 1.9 gives relative paths in __FILE__? Maybe we should just special-case expand_path for Ruby 1.9 then?

@Sod-Almighty
Copy link

What about SCRIPT_LINES__?

onlynone added a commit to onlynone/pry that referenced this issue Apr 23, 2024
@onlynone onlynone linked a pull request Apr 23, 2024 that will close this issue
onlynone added a commit to onlynone/pry that referenced this issue Apr 23, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

5 participants