I want to perform several operations while working on a specified virtualenv.
For example command
make install
would be equivalent
You should use this, it's functional for me at moment.
report.ipynb : merged.ipynb
( bash -c "source ${HOME}/anaconda3/bin/activate py27; which -a python; \
jupyter nbconvert \
--to notebook \
--ExecutePreprocessor.kernel_name=python2 \
--ExecutePreprocessor.timeout=3000 \
--execute merged.ipynb \
--output=$< $<" )
I have had luck with this.
install:
source ./path/to/bin/activate; \
pip install -r requirements.txt; \
In make you can run a shell as command. In this shell you can do everything you can do in a shell you started from comandline. Example:
install:
( \
source path/to/virtualenv/bin/activate; \
pip install -r requirements.txt; \
)
Attention must be paid to the ;
and the \
.
Everything between the open and close brace will be done in a single instance of a shell.
Normally make
runs every command in a recipe in a different subshell. However, setting .ONESHELL:
will run all the commands in a recipe in the same subshell, allowing you to activate a virtualenv and then run commands inside it.
Note that .ONESHELL:
applies to the whole Makefile, not just a single recipe. It may change behaviour of existing commands, details of possible errors in the full documentation. This will not let you activate a virtualenv for use outside the Makefile, since the commands are still run inside a subshell.
Reference documentation: https://www.gnu.org/software/make/manual/html_node/One-Shell.html
Example:
.ONESHELL:
.PHONY: install
install:
source path/to/virtualenv/bin/activate
pip install -r requirements.txt
Based on the answers above (thanks @Saurabh and @oneself!) I've written a reusable Makefile that takes care of creating virtual environment and keeping it updated: https://github.com/sio/Makefile.venv
It works by referencing correct executables within virtualenv and does not rely on the "activate" shell script. Here is an example:
test: venv
$(VENV)/python -m unittest
include Makefile.venv
Differences between Windows and other operating systems are taken into account, Makefile.venv should work fine on any OS that provides Python and make.
I like using something that runs only when requirements.txt
changes:
This assumes that source files are under project
in your project's root directory and that tests are under project/test
. (You should change project
to match your actually project name.)
venv: venv/touchfile
venv/touchfile: requirements.txt
test -d venv || virtualenv venv
. venv/bin/activate; pip install -Ur requirements.txt
touch venv/touchfile
test: venv
. venv/bin/activate; nosetests project/test
clean:
rm -rf venv
find -iname "*.pyc" -delete
make
to install packages in requirements.txt
.make test
to run your tests (you can update this command if your tests are somewhere else).make clean
to delete all artifacts.