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

[Question] Configuring direnv using .envrc #331

Closed
devonhk opened this issue Feb 15, 2018 · 10 comments
Closed

[Question] Configuring direnv using .envrc #331

devonhk opened this issue Feb 15, 2018 · 10 comments

Comments

@devonhk
Copy link

devonhk commented Feb 15, 2018

Issue description

I want to use direnv to automatically activate python-virtualenvs when I cd into a directory containing one.
I have a few questions after going through the docs.

  1. From what I read I need to create .envrc. What I don't understand is where to put this file, does it go in my $HOME dir or do I have to create one per project repo?

  2. Does the .direnvrc serve the same purpose as the .envrc ?

I looked at the virtualenv examples here https://github.com/direnv/direnv/wiki/Python#-virtualenv
but it isn't clear to me what direnv is doing.

@zimbatm
Copy link
Member

zimbatm commented Feb 16, 2018

direnv gets executed before every prompt line in your shell once it's hooked into your shell. when it's executed it looks for the .envrc file in the current and parent directories and acts accordingly.

If the .envrc is found, and it's authorized, it loads the stdlib, the direnvrc (if exists) and finally the envrc files in a bash sub-shell. Then it looks at the environment and applies the diff to your current shell (and saves the original values).

If the .envrc is not found or has changed, it will restore the original environment variable values.

This is basically the core of how direnv works and which allows to have dynamic environment variables depending on the current directory.

To answer your question more specifically: create a new .envrc per project to set the virtualenv path that you want to use. The stdlib already provides a bunch of helpers, in your case adding layout python to the .envrc might just be enough. If that doesn't suit you then override the default or create new functions in the direnvrc file.

has three levels of functionality: stdlib, direnvrc and envrc.

The .direnvrc is a global shell script that you can use to provide shared the

@devonhk
Copy link
Author

devonhk commented Feb 20, 2018

Thanks for explaining the direnv workflow. But is this module https://github.com/direnv/direnv/wiki/Python#-virtualenv the only way to activate virtualenvs ?

The docs say it will automatically create a virtualenv here .direnv/python-$python_version, but I don't want virtualenvs to be magically created for me, I just want to specify a path to a virtualenv to be activated.
Is this possible with the stdlib?

Thanks

@zimbatm
Copy link
Member

zimbatm commented Feb 20, 2018

Sure. "activating" a virtualenv is basically doing two things, so you can add those in your .envrc:

export VIRTUAL_ENV=path/to/your/virtualenv
PATH_add "$VIRTUAL_ENV/bin"

If you are tired of copying those around, make a function in your ~/.config/direnv/direnvrc file:

activate_virtualenv() {
  export VIRTUAL_ENV=$1
  PATH_add "$VIRTUAL_ENV/bin"
}

and then in your .envrc:

activate_virtualenv path/to/virtualenv

@devonhk
Copy link
Author

devonhk commented Feb 20, 2018

Thanks for the quick reply. I should probably read up on bash scripting.
Last question, I noticed I don't have a virtualenv prompt when direnv activates a virtualenv.

ex : (venv) user@user ~/code/project> instead my prompt looks like user@user ~/code/project>
Is there a way to have direnv display the prompt for me, or will I have to configure this in my own shell (fish)?

@zimbatm
Copy link
Member

zimbatm commented Feb 20, 2018

Yeah I guess direnv is best suited to you if you know a little of bash.

virtualenv also sets the PS1 environment variable in the activate script. PS1 is on the direnv blacklist because of a bug in bash 3.x on macOS so you would have to implement it yourself. I don't have an example at hand but it's possible to change the prompt depending on if VIRTUAL_ENV is set or not. In general I don't find it very useful but that's personal.

@devonhk devonhk closed this as completed Mar 12, 2018
@mathcass
Copy link

@pydo, I came across this thread and learned a bit. Thank you for asking about it and for @zimbatm's answer about PS1.

It looks like some info for changing the prompt is in the wiki (in case you were looking for some workarounds).

@mals14
Copy link

mals14 commented Jan 17, 2019

@pydo did you learn how to change PS1 in fish shell when using direnv to activate a virtual environment? Thanks.

@devonhk
Copy link
Author

devonhk commented Feb 2, 2019

@mals14 I just use a fish theme that does it auto-magically for me https://github.com/oh-my-fish/oh-my-fish/blob/master/docs/Themes.md#lambda .
EDIT
I'm not sure why this PS1 var is needed, I just checked my theme's source code and all it does it check if VIRTUAL_ENV is set, if so it displays it in the left prompt https://github.com/hasanozgan/theme-lambda/blob/master/fish_prompt.fish#L61

@mals14
Copy link

mals14 commented Feb 2, 2019

@pydo

Thanks for the reply. For some reason lambda prompt works very well for me until I am in a normal directory. Once I enter into a virtual environment directory, then the prompt simply changes to ">". Must be something with my settings somewhere.

Bobthefish theme seems to work. Although I like lambda for its two line and full display path. But lambda does not work. I have fish 3.0, and latest stable omf and lambda theme. :(

@mals14
Copy link

mals14 commented Feb 5, 2019

Sure. "activating" a virtualenv is basically doing two things, so you can add those in your .envrc:

export VIRTUAL_ENV=path/to/your/virtualenv
PATH_add "$VIRTUAL_ENV/bin"

If you are tired of copying those around, make a function in your ~/.config/direnv/direnvrc file:

activate_virtualenv() {
  export VIRTUAL_ENV=$1
  PATH_add "$VIRTUAL_ENV/bin"
}

and then in your .envrc:

activate_virtualenv path/to/virtualenv

@zimbatm a question if you can help.

I create virtual environment using python3 -m venv ..
Then I create a .envrc that has layout python-venv.
I have already created a function the function layout_python-venv() {... in ~/.config/direnv/direnvrc.
It feels like to me that direnv creates its own virtual env and the python3 -m venv command is superfluous at this point.
Am I right?

And if my understanding is right, then would this second approach that you advised earlier in the thread help avoid the creation of venv by direnv.

For the Fish shell:

Create a function like so in functions directory

function activate_virtualenv
	set -x VIRTUAL_ENV $argv
	set PATH "$VIRTUAL_ENV/bin" $PATH
end

And then .envrc be

activate_virtualenv /Users/smalani/Documents/scripts-programming/python-code/analyze-keywords-in-logs.py

Sounds like to me that using the second approach avoids the need to have the function layout_python-venv() {... in ~/.config/direnv/direnvrc. And the second approach does not create the virtual environment again.

Which one do you advise? Thanks.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

No branches or pull requests

4 participants