Pin `pipenv install X` to compatible version of X in Pipfile instead of *
See original GitHub issueIs your feature request related to a problem? Please describe.
In my experience, pipenv
seems to be a bit too eager to update to newer versions of dependencies (see e.g. #1219). Based on other tools like cargo
and npm
, I would expect pipenv install
in a newly checked out project to get me a working environment for running the project. However, since pipenv install X
pins to X = "*"
in the Pipfile, it is possible that I’ll get newer versions of the deps incompatible with the given project.
Describe the solution you’d like
See also https://github.com/pypa/pipenv/issues/1219#issuecomment-360690738:
Maybe Pipenv should do what npm does and make
pipenv install
pin to the major version instead of'*'
.
I think it would be great if pipenv install X
pinned to X = "~=<current_version>"
instead of X = "*"
, ideally by default (but I admit my perspective may be limited by my particular use cases) or at least through an option that can be specified on the command line and/or in the Pipfile itself, something like --pin-to-current
/ pin_to_current = true
.
Describe alternatives you’ve considered
What I’m doing currently is trying to remember to run pipenv install --ignore-pipfile
instead of pipenv install
when setting up a project for development on a new machine. However, this skips all updates, even compatible ones (bug / security fixes etc.), since the purpose of --ignore-pipfile
is deterministic builds for production, not setting up a compatible environment for development.
Issue Analytics
- State:
- Created 5 years ago
- Reactions:20
- Comments:20 (11 by maintainers)
The general proposition of using
~=
(or even^=
, which does not exist in pip) is still valid, and I have seen this raised quite a few times now.*
means every re-lock and update could potentially break user code because a new major version is released and it is not compatible with the application.You could argue the user should be aware of this, and use e.g.
django~=2.1.0
in the first place. But still, there is no good way to say “I want the latest ~= possible” instead of manually looking it up. It would be immensely helpful to either a) set this as default, and requiredjango==*
to explicitly get*
, or b) have a command flag as mentioned above (an option in Pipfile less so IMO).While the problem described is probably fixed, the user experience side of this proposition is still worth discussing.
Sorry, I should have given a more concrete user story in the OP to make the issue clearer 😃 For instance:
pipenv install flask
. This putsflask = "*"
in my Pipfile and installs the latest version of flask, say0.12.3
.pipenv install --ignore-pipfile
to get the exact same dependencies as those used in development).pipenv install
: this will install the latest flask1.0.2
, which may very well have some incompatibilities with0.12.3
, the version my project was originally developed withpipenv install --ignore-pipfile
(like when deploying): this will install the original version0.12.3
of flask, but in the meantime,0.12.4
has also been released, which should be compatible with the originally used version but probably contains bug and security fixes that I shouldn’t ignore…Pipfile.lock
, changeflask = "*"
in thePipfile
toflask = "~=0.12.3"
, and onlye then dopipenv install
, which will get me flask0.12.4
I think the last behavior is the most useful one, yet it is the hardest one to achieve (the only one which involves manual operations). If the goal of the current default behavior of
pipenv install
(see first bullet above) is to nudgepipenv
users towards ditching obsolete dependencies, I think that could be achieved in a less jarring way by just warning them that a newer version exists but won’t be installed because of compatibility requirements.As @uranusjr says, it’s a user experience issue:
I couldn’t agree more.
Another possibility is that I’m using
pipenv
completely wrong, in which case please point out the problems with the workflow above and I’ll think about how the docs could be improved to better communicatepipenv
’s intended usage patterns 😃