Do we need two version-locking files? (Pipfile = "*" vs pypoetry.toml vs venv + requirements.txt)
Tags: discuss, python, healthydebate, programming
Published: 2021-10-05 05:29:47

**Edit:** I am also confused about `.venv/bin/python`'s location - in-project ``$PROEJCT_ROOT/.venv/bin/python`` or global (e.g. `~/.pyenv/versions/$PROJECT_IDENTIFIER/.venv/bin/python`)?

## Pipenv's defaults

I feels odd to me that my `Pipfile` looks like this.

```toml
[[source]]
url = "https://pypi.org/simple"
verify_ssl = true
name = "pypi"

[packages]
fastapi = "*"
aiofiles = "*"
uvicorn = "*"
gunicorn = "*"
gtts = {git = "https://github.com/patarapolw/gTTS.git"}
wordfreq = {extras = ["cjk"], version = "*"}

[dev-packages]

[requires]
python_version = "3.9"
```

To say that, if you know lock files in other programming languages' package managers; this looks **VERY OPINIONATED**.

Of course, there is `Pipfile.lock`, but it doesn't look very readable to me, unlike `package.json` or `go.mod` (which, of course, have `package.lock` and `go.sum` to pair with).

Another problem is, Pipenv IS NOT VERY VERBOSE at all...

Personally, I also add `export PIPENV_VENV_IN_PROJECT="enabled"
` to `~/.zshrc`.

## `python -m venv .venv`

This path typically creates only one version-locking - `requirements.txt`; and it can be readable, if not compiled directly from `pip freeze >`.

I have seen some projects with multiple `requirements.txt` (e.g. `.prod.txt`, `.dev.txt`); but I have seen **NONE** with `requirements.lock`

But of course, it is as easy as `pip freeze > requirements.lock`; even perhaps adding to git pre-commit hook.

```sh
cat << EOF > ~/.git/hooks/pre-commit
#!/usr/bin/env bash
source .venv/bin/activate
pip freeze > requirements.lock
EOF

chmod +x ~/.git/hooks/pre-commit
```

Personally, I don't really use this option much.

## Poetry's opinionatedness

`poetry add <PACKAGES>` actually pin versioning into TWO lock files, one with exact, another with `>=`; but I distaste this.

```
$ poetry init
...
Would you like to define your main dependencies interactively? (yes/no) [yes] no
Would you like to define your development dependencies interactively? (yes/no) [yes] no
...
```

So, you wanted me to answer YES, huh?

Personally, I am add config,

`poetry config set virtualenvs.in-project true`.

## semver syntax I learnt from JavaScript Node.js

So, in Node.js, we have something like this.

```
>=2.0.1
^2.0.1
~2.0.1
2.0.1
2.0
2
```

Not sure about these syntaxes in Python, and whether it is just `requirements.txt` (TXT file), `setup.py` (Python file), or whatever `*.toml` files.

## Do we still need `setup.py`; if we are not publishing to PyPI or local repository?

I don't know the answer to this either...

But of course, it can help with py2app or py2exe; which I don't need when I already have PyInstaller.

## A thought

Why can't we just go back to

```sh
cat << EOF > requirements.txt
fastapi
aiofiles
EOF

python -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
pip freeze | grep -i "$(cat requirements.txt)" > requirements.txt
pip freeze > requirements.lock
python --version > .python-version

# Then, hand-edit requirements.txt
```

## What is YOUR decision?

For me, even though I like Poetry, I don't like some of the defaults; but the general defaults of other options are even more insane.

How would you deviate from the default settings?