mise: `rtx activate` incompatible with direnv
I started playing with rtx today to replace my asdf-direnv setup.
When using layout python3 from the direnv stdlib, it used my global rtx python3 version and not the rtx local one. In the shell itself, the venv of direnv wasn’t used, as rtx added the configured path sections to the fron of PATH.
Updated: My fix was to move The work-around is only working in the folder containing .envrc and .tool-versions, but not in subfolders (see comment below):eval "$(rtx activate -s zsh)" after my direnv one in .zshrc
eval "$(direnv hook zsh)"
eval "$(rtx activate -s zsh)"
Is this something for a known-issues/documentation section or can the zsh call sequence somehow be influenced?
Thank you for this initial release of rtx. It’s a great start.
Reproduce:
~/.tool-versions:
python 3.10.9
.zshrc
eval "$(rtx activate -s zsh)"
eval "$(direnv hook zsh)"
~/dev/tmp/rtx-direnv/.envrc:
layout python3
~/dev/tmp/rtx-direnv/.tool-versions:
python 3.8.10
Steps:
❯ echo $PATH
/Users/user/.local/share/rtx/installs/python/3.10.9/bin:/opt/homebrew/opt/mysql-client/bin:/opt/homebrew/bin:/opt/homebrew/sbin:/usr/local/bin:/System/Cryptexes/App/usr/bin:/usr/bin:/bin:/usr/sbin:/sbin:/Library/Apple/usr/bin:/Users/user/.rd/bin:/opt/homebrew/opt/fzf/bin
❯ cd ~/dev/tmp/rtx-direnv
direnv: error /Users/user/Projects/tmp/rtx-direnv/.envrc is blocked. Run `direnv allow` to approve its content
# after the initial `direnv allow` it will seem to work, as the path is already adjusted by rtx
❯ direnv allow
direnv: loading ~/Projects/tmp/rtx-direnv/.envrc
direnv: export +VIRTUAL_ENV ~PATH
❯ cd ..
direnv: unloading
❯ cd ~/dev/tmp/rtx-direnv
direnv: loading ~/Projects/tmp/rtx-direnv/.envrc
direnv: export +VIRTUAL_ENV ~PATH
# direnv venv path overwritten and venv pointing to wrong python version
❯ echo $PATH
/Users/user/.local/share/rtx/installs/python/3.8.10/bin:/Users/user/Projects/tmp/rtx-direnv/.direnv/python-3.10.9/bin:/opt/homebrew/bin:/Users/user/bin:/Users/user/go/bin:/Users/user/.local/bin:/Users/user/.cargo/bin:/opt/homebrew/opt/mysql-client/bin:/opt/homebrew/bin:/opt/homebrew/sbin:/usr/local/bin:/System/Cryptexes/App/usr/bin:/usr/bin:/bin:/usr/sbin:/sbin:/Library/Apple/usr/bin:/Users/user/.rd/bin:/opt/homebrew/opt/fzf/bin
With updated .zshrc:
eval "$(direnv hook zsh)"
eval "$(rtx activate -s zsh)"
Steps:
# open new shell
❯ cd ~/dev/tmp/rtx-direnv
direnv: loading ~/Projects/tmp/rtx-direnv/.envrc
direnv: export +VIRTUAL_ENV ~PATH
❯ echo $PATH
/Users/user/Projects/tmp/rtx-direnv/.direnv/python-3.8.10/bin:/Users/user/.local/share/rtx/installs/python/3.8.10/bin:/opt/homebrew/bin:/Users/user/bin:/Users/user/go/bin:/Users/user/.local/bin:/Users/user/.cargo/bin:/opt/homebrew/opt/mysql-client/bin:/opt/homebrew/bin:/opt/homebrew/sbin:/usr/local/bin:/System/Cryptexes/App/usr/bin:/usr/bin:/bin:/usr/sbin:/sbin:/Library/Apple/usr/bin
About this issue
- Original URL
- State: closed
- Created a year ago
- Reactions: 2
- Comments: 59 (56 by maintainers)
Commits related to this issue
- direnv via externalfiles When direnv is installed via homebrew, it automatically hooks in fish (via linking activation script in /opt/homebrew/share/fish), but in order to make it work nicely with rt... — committed to delicb/dotfiles by delicb a year ago
- adds asdf-clickhouse to registry (#8) * adds asdf-clickhouse to registry * updates README with Clickhouse — committed to jdx/mise by collegeimprovements 4 months ago
@jdxcode I quickly checked
rtx-pythonplugin fork. I found two problems:It might be that only subset of these is needed, but I tried couple of combinations and virtualenv kept being activated until I executed all of these, but since I am not sure why this happens, I am not sure if all of these are required.
cd-ed directly. E.g. if I have~/myprojthat contains file.rtx.tomland directorysubdirand I docd myproj/subdir, it creates virtualenv in subdir, when it should be in project root.I can open ticket in https://github.com/jdxcode/rtx-python if you wish to track it there, but I think replacing
layout pythonwill be more involved than current implementation ofexec-env. I would love to usevirtualenvparameter in.rtx.toml, but for example I have override fordirenv_layout_dirto create virtualenvs in$XDG_CACHE_HOME/direnv/layouts/<project-name>, whichdirenvsupports out of the box. There are probably more such features which would complicate python asdf plugin.think there is a typo: you’re recommending the second
rtx activate, not the firstrtx direnv activateagreed on all points. I think a shim mode may make sense, it wouldn’t be that hard to do. I wouldn’t make it the default of course.
added more information around this to the readme in bb61bc5. I’m probably going to focus on other things (like
rtx where) when I can focus on rtx development for now. If people are having issues like with what @amoosbr has outlined above (or other issues) go ahead and comment on this ticket.I think we’ve sorted out the major issues with
rtx activateanddirenv hookfor now.In my initial test this morning the issues, I wasn’t able to reproduce any of the issues mentioned before.
I just add here a few comments for usage reference:
Hook order
In my experience, its still relevant and for
zshshould look like:.zshrc:For zsh, you can verify hook order via
echo $chpwd_functionsand_rtx_hookshould be listed before_direnv_hook.Perhaps in a documentation update, when this issue gets close?
PATH order gets modified and can break custom dev workflows
I have no idea, how common these scenarios are and if you @jdxcode think, they are working as expected, are to worked on within this issue or should be in their own new issue to collect feedback. I can also try to create an e2e test case, if the order should be kept. I think keeping the PATH order (what was added before rtx paths and after rtx) would avoid scenarios 1. and 2. If it’s how
rtxshould behave. Example 3. is something, I think rtx can not do much about..envrcused in samples:A bit interesting for a user to predict. It’s probably related to rtx not keeping the PATH order (before/after rtx) mentioned in this comment and not related just to direnv.
-> workaround change out of the direnv managed directory and back in
.tool-versionsfile and back to the previous directoryWhen traversing to subproject with new
.tool-versionsfile. Which tool added, is irrelevant. -> workaround, where needed: add.envrcwith i.e.source_up_if_existsor change out of the direnv managed directory and back inThis will anyway be complicated to automate in combination with direnv, as direnv doesn’t watch .tool-versions file. -> If common, add
watch_fileto local.envrcfile or useuse rtx) -> Corner case, that a user can decide, how to handle@amoosbr how are you controlling which version of python you want to use for project? Via local
.tool-versions? I have both 3.10 and 3.11 installed and use different versions for different project, so this is my way to explicitly set right version so thatlayout pythoncan pick it up. I guess.tool-versionswould work as well.Edit: I just tried using
rtx local python@3.10which creates.tool-versionslocally and it seem to work just like my approach withuse python. Still not sure which one I prefer better, will decide over time, both seems to be working.@amoosbr Thanks, you are right, order is relevant. However, for me, order of hooks that works is different:
Works, while if I set it the other way around, I always get python from
$HOME/.local/share/rtx/installsfirst in path.Maybe it has something to do with the shell (I see you are using
zshand I am usingfish).@jdxcode thanks for clarification. What i did was to uninstall direnv installed via homebrew and download binary directly, so that I can control the moment hooks are initiated (since order matters).
I have created
$HOME/.config/direnv/lib/use_python.shwith following content (based on your suggestion and similar to other toolsdirenvsupports withusefunction):So my
.envrcnow looks like:and as far as I can tell, this are working as expected now.
Thanks for all the time you spent on this issue 🙌
Ok one more crazy idea—this one really is bonkers.
In theory
rtxcan be named whatever you want. The CLI is a single file and whatever its name is is its name. That means you can name itasdf. If you didmv ~/bin/rtx ~/bin/asdfthen you could install asdf shims with rtx because they would be callingasdf execbut that would actually be launching rtx.However the commands between the 2 are not identical. They might be close enough though. I’d be happy to find out places were there are miscompatibilities and see how we could get them to align, even if we had to use some sort of “compat” mode. We might need this anyways since plugins commonly call
asdf.You could also do a hybrid approach and create an
asdfbinary that is your own shim. If it is called withasdf exec, then it dispatches to rtx for speed, if it’s anything else it dispatches to asdf. You would probably want to setRTX_DATA_HOME=$HOME/.asdf—which may or may not function very well.Anyways I realize this is probably way too much information but as you can tell I’m still trying to think of how best to handle this situation. If you have some time to experiment with any of these ideas please let me know how it goes. I wish this would’ve been as simple as me just patching rtx to not conflict with direnv but I think that might be challenging.
I suppose one other idea is for me to reach out to direnv and see if they have any ideas.
@jdxcode Thanks for your response.
@amoosbr mentioned switching order worked for him, that is what I was referring to. I am not planning using
asdf-direnvplugin with rtx, I just mentioned it as mental exercise 😃Thanks for the snippet, I will give it a try.