tox: virtualenv is not recreated when deps change if '-r' is used
- Bitbucket: https://bitbucket.org/hpk42/tox/issue/149
- Originally reported by: @gavrie
- Originally created at: 2014-01-28T15:36:07.365
In my tox.ini, I have the following deps:
deps = -rpackaging/requirements.txt
Normally, when deps change, the virtualenv is recreated by tox. However, when the contents of requirements.txt change, tox does not notice this and the environment is reused.
A workaround would be to list the deps directly in tox.ini, but that would require duplicating the contents of the existing requirements.txt that is used by other tools.
About this issue
- Original URL
- State: closed
- Created 8 years ago
- Reactions: 74
- Comments: 96 (50 by maintainers)
Commits related to this issue
- Add tox-pip-extensions and use venv-sync for tox See: https://github.com/tox-dev/tox/issues/149#issuecomment-298282944 — committed to dotkom/onlineweb4 by sklirg 6 years ago
- recreate tox environments if we detect changes to requirements files we do this, since tox amazingly enough is not able to detect changes to requirements files itself. see https://github.com/tox-dev/... — committed to Uninett/nav by lunkwill42 6 years ago
- recreate tox environments if we detect changes to requirements files we do this, since tox amazingly enough is not able to detect changes to requirements files itself. see https://github.com/tox-dev/... — committed to Uninett/nav by lunkwill42 6 years ago
- build: avoid missing to install new deps Workaround tox bug https://github.com/tox-dev/tox/issues/149 — committed to pycontribs/jira by ssbarnea 6 years ago
- build: avoid missing to install new deps Workaround tox bug https://github.com/tox-dev/tox/issues/149 — committed to pycontribs/jira by ssbarnea 6 years ago
- Use venv_update to auto update virtualenvs Use the venv_update tox plugin from tox-pip-extensions (https://github.com/tox-dev/tox-pip-extensions) to automatically update tox's Python virtualenvs in d... — committed to hypothesis/h by seanh 6 years ago
- Use venv_update to auto update virtualenvs Use the venv_update tox plugin from tox-pip-extensions (https://github.com/tox-dev/tox-pip-extensions) to automatically update tox's Python virtualenvs in d... — committed to hypothesis/h by seanh 6 years ago
- Create requirements.txt and switch to setuptools Although https://github.com/tox-dev/tox/issues/149 is still not resolved, requirements.txt are extracted now, as this is the usualy way. — committed to mrh1997/headlock by mrh1997 6 years ago
- Upgrade flake8 to 3.6.0 Upgrade flake8 in order to avoid undesired warning inside pycodestyle. Adopts workaround for https://github.com/tox-dev/tox/issues/149 in order to avoid missing to update req... — committed to ssbarnea/molecule by ssbarnea 6 years ago
- mgr/dashboard: fix: tox not detecting deps changes * tox.ini: replaced 'deps' setting by appropriate commands due to this bug: https://github.com/tox-dev/tox/issues/149 tox is not detecting cha... — committed to rhcs-dashboard/ceph by alfonsomthd 5 years ago
- Update deps, and embed dev deps directly in tox to avoid a tox bug (https://github.com/tox-dev/tox/issues/149) — committed to pachyderm/python-pachyderm by ysimonson 5 years ago
- [travis] caching: add caching (but will remove again because of https://github.com/tox-dev/tox/issues/149) — committed to thomasjahoda/cookiecutter-pypackage by thomasjahoda 5 years ago
- Revert "[travis] caching: add caching (but will remove again because of https://github.com/tox-dev/tox/issues/149)" This reverts commit 83b73c8aa3affe91916b35eecebe6c99439014d8. — committed to thomasjahoda/cookiecutter-pypackage by thomasjahoda 5 years ago
- Make tox notice dependency changes When passing dependencies via a file such as: deps = -rtest-requirements.txt Tox is unable to notice a change, it does not include pip to parse the dependenci... — committed to wikimedia/integration-zuul-config by hashar 5 years ago
- Recreate tox envs https://github.com/tox-dev/tox/issues/149 — committed to python-jsonschema/hypothesis-jsonschema by Zac-HD 5 years ago
- Rebuild tox environment after change requirements Tox does not detect changes in requirements, and will fail with missing imports. [example](https://saml.buildvm.openshift.eng.bos.redhat.com:8888/job... — committed to joepvd/elliott by joepvd 4 years ago
- Rebuild tox environment after change requirements Tox does not detect changes in requirements, and will fail with missing imports. [example](https://saml.buildvm.openshift.eng.bos.redhat.com:8888/job... — committed to joepvd/elliott by joepvd 4 years ago
- Don't overload deps: It's slower but ensures we use the pinned ones. Also use pip-sync, to avoid having to use `tox -r` when we change or upgrade our requirements, see: https://github.com/tox-dev/tox... — committed to JulienPalard/oeis by JulienPalard 3 years ago
- dockerfiles: operations-puppet: upgrade tox to 4.8.0 The operations-puppet Docker image holds Python dependencies by running `tox --notest` on build. However when a change is made to one of the requi... — committed to wikimedia/integration-zuul-config by hashar 10 months ago
I’ll have to disagree - this is an issue I hear from various people, and it’s quite unexpected. I view it as “tox does caching without invalidating the cache correctly” essentially. The core does caching, so I think it really should do this correctly.
Just to give an update of this. There has been a significant discussion going on upstream to build backends to offer dependency information (and other metadata) without a build happening. Once this takes shape we’ll be able to implement the feature request here in a reliable fashion. I plan to push this through so should be addressed by the end of the year (my plan as of now).
I hope this bug does not endup closed before we have this fixed inside tox itself. We should not endup using external tools or hacking tox.ini in order to get around it (workaround which mainly disables the deps option in tox).
It’s a fairly complicated issue, it’s more like adding a major feature than hotfix. We have an alpha version of it https://pypi.org/project/tox/4.0.0a2/, a first public release expected in a few months.
It is indeed https://github.com/jazzband/pip-tools
tox.ini:
pip-sync makes sure new dependencies or updated versions are installed in the virtualenv and removes old dependencies. I don’t duplicate dependencies in tox.ini, I never have to recreate the testenvs, my co-workers never have failures because requirements.txt changed. My deployment also uses pip-sync.
Article from the original developer of pip-tools: http://nvie.com/posts/better-package-management/
pip-tools very recently gained the ability to generate requirements.txt with pinned versions from dependencies in setup.py, so you can have a lib with loose requirements in setup.py and exact pinned versions in requirements-test.txt for your tox testing.
Original comment by @Merwok
This also happens if dependencies in setup.py (install_requires) change.
That’d be horrible IMHO, and keep a lot of projects (including mine) from using tox
This approach has been discussed before (probably multiple times by now?) in this thread. The main problem is that requirement files can include others via
-r, which still wouldn’t be fixed by a “naive” approach. However, I’d argue that even a naive approach which doesn’t deal with requirement files including others would be a big benefit.Yes, and it’s planned for tox 4 🤔
Removing the
-rsupport would immediately break CI for a lot of people (almost nobody uses a pinnedtox), and is a pretty important feature about tox, IMHO.@gaborbernat How about adding a
fixed-by-tox4label and also locking the ticket? There are lots of other similar tickets which are solved by it and which will not be addressed by old version. I you give me triage rights, I could help with that.Could
toxhash anyrequirements.txtfiles that are used and cache that? Then it could know if the file had changed and recreate if necessary.I’ve implemented a tox plugin to hook up venv-update to make it so
tox -ris unnecessary. From my cursory testing, it seems to work pretty well:It’s a little rough around the edges:
install_commandof all testenvsinstalldepsstep to preinstall the required bootstrap packages (in this casevenv-updateand its dependencies)pretesthook which--prunes extraneous dependenciesbut it seems to work
This test demonstrates the acceptance criteria described in this ticket: https://github.com/asottile/tox-pip-extensions/blob/4d0ccaae3d68495d2d3e7c1bdb78102f0d6fafae/tests/tox_pip_extensions_test.py#L166-L182
we once had better support for requirements parsing but we had to revert it … i admit i never extensively used -r requyirements.txt myself and the docs still mark that feature as experimental http://tox.readthedocs.io/en/latest/example/basic.html?highlight=requirements#depending-on-requirements-txt – someone needs to step up to go for it more properly … meanwhile recommending to manually use “tox -r” for recreating an env is a kludge to get around tox’s ignorance.
Original comment by mhirota
What about recognizing the special case of
deps = -r<something>and calculating the md5 based on the file contents? This would trigger recreate if anything in therequirements.txtchanged… but I think that might be better than duplicating what is inpipor introducing a hard dependency onpipintox.I’ve wanted to take
pip-faster install --prune, upstream it, and then use it for this purpose (probably aspip prune? similar tonpm prune). But I haven’t really had the time or motivation (and sadly we don’t use tox at work so I can’t even float it there 😕). Until then, I’ve used tox-pip-extensions with the venv-update extension to work around this+1for @asottile’stox-pip-extensionsas a solution to this problem, though obviously it would still be nice to have it fixed intoxout of the boxDefinitely. IMHO it is way past the “experimental” stage where it could be removed. Removing it would break tons of test suites everywhere.
disclaimer: I’m not (yet) familiar with tox’s internals and its design philosophy and AFAIK it is my first interaction with the project
Would a
Makestyle, last-modified-time (dependencies vs. ‘sources’) based approach be an acceptable solution here? I.e.: inVirtualEnv.update, instead of using onlyself.envconfig.recreate, use(self.envconfig.recreate or should_recreate_based_on_last_modified_times())(or store into a variable/method for brevity)? It could check the-rfile as well as thesetup.pyin the root folder (*).Granted, its performance wouldn’t be as good as a smart solution’s, but it would produce a correct venv
* and I know there can be weird corner cases with editable dependencies having their own
setup.pyfiles that can change, or the repo having multiplesetup.pyfiles, etc., but those could be fixed iteratively, by expanding the list of files to check for timestampsedit: or is this suggestion better suited for #93?
@merwok that sounds interesting, but I have no idea what you are talking about - could you link to some documentation/blog/howto/whatever with more details about this approach? Thanks!
Order is significant in requirements files (for now at least — Pip’s new resolver may change that).
@gaborbernat Really nice to hear you aim to nail it! On the other hand I realise that we are in March… so the end of the year is not as near as I would have wished for.
Ah I see, you’re misunderstanding how
pip-syncworks.From https://github.com/jazzband/pip-tools#example-usage-for-pip-sync
@obestwalter regarding the non working
extrasit’s actually my fault, the system where I was having the issue had tox 2.3.1 installed system-wise, and I cannot reproduce it with tox 2.5.0 or 2.7.0. Sorry about the misunderstanding.As already stated, this doesn’t change the main issue here, that the dependencies are not updated. Anyway thanks for the tip.
Thanks for working on this!
Independently of the specific solution chosen, please consider to make it work also for keeping dependencies up to date when installed from
setup.py, I think that this is also a fairly standard use case.To be explicit I’m referring to the usage of
deps = .to install theinstall_requiresdependencies ordeps = .[key_in_extras_require]to install theinstall_requiresdependencies plus the ones defined inextras_require['key_in_extras_require'].In the end I’m seeing this as a cache issue on tox side, given that there are at least three working syntaxes to install dependencies , of which only one express them explicitly, while the others get them indirectly and tox is not able to detect changes or available updates in the indirect cases.
I think the
-rthat’s being talked about here is the one indeps =and not the command line one.However wouldn’t it be more sensible to keep the
-rdeps capability but instead of reinventing the wheel just rely on pip-tools for the job? From a quick look at the source it seems as if using it as a library should be pretty easy (although maybe not officially supported?)@obestwalter pip-tools can be used to keep a virtualenv exactly in sync with the requirements.
It’s really a great idea to use it in tox. Should have thought of that myself.
@obestwalter one approach (that we’re using internally, and will have a better solution for once 2.7.0 ships with my plugin changes 😄) is to use https://github.com/Yelp/venv-update – pip-faster has a
--prunewhich will uninstall extraneous dependencies (and ensure the installed state is exactly what was on the cli)Original comment by wbyoung
@wmyll6 thanks for the plugin. Hopefully some of that work can make its way into the core!