diff --git a/README.rst b/README.rst index 833f779dc..3aabfed66 100644 --- a/README.rst +++ b/README.rst @@ -50,7 +50,8 @@ Example usage for ``pip-compile`` ================================= The ``pip-compile`` command lets you compile a ``requirements.txt`` file from -your dependencies, specified in either ``setup.py`` or ``requirements.in``. +your dependencies, specified in either ``pyproject.toml``, ``setup.cfg``, +``setup.py``, or ``requirements.in``. Run it with ``pip-compile`` or ``python -m piptools compile``. If you use multiple Python versions, you can also run ``py -X.Y -m piptools compile`` on @@ -67,39 +68,105 @@ available. To compile from scratch, first delete the existing ``requirements.txt`` file, or see `Updating requirements`_ for alternative approaches. -Requirements from ``setup.py`` ------------------------------- +Requirements from ``pyproject.toml`` +------------------------------------ -Suppose you have a Django project, and want to pin it for production. -If you have a ``setup.py`` with ``install_requires=['django']``, then run -``pip-compile`` without any arguments: +The ``pyproject.toml`` file is the +`latest standard `_ for configuring +packages and applications, and is recommended for new projects. ``pip-compile`` +supports both installing your ``project.dependencies`` as well as your +``project.optional-dependencies``. Thanks to the fact that this is an +official standard, you can use ``pip-compile`` to pin the dependencies +in projects that use modern standards-adhering packaging tools like +`Hatch `_ or `flit `_. -.. code-block:: bash +Suppose you have a Django application that is packaged using ``Hatch``, and you +want to pin it for production. You also want to pin your development tools +in a separate pin file. You declare ``django`` as a dependency and create an +optional dependency ``dev`` that includes ``pytest``: - $ pip-compile +.. code-block:: toml + + [build-system] + requires = ["hatchling"] + build-backend = "hatchling.build" + + [project] + name = "my-cool-django-app" + version = "42" + dependencies = ["django"] + + [project.optional-dependencies] + dev = ["pytest"] + +You can produce your pin files as easily as: + +.. code-block:: console + + $ pip-compile -o requirements.txt pyproject.toml # - # This file is autogenerated by pip-compile + # This file is autogenerated by pip-compile with python 3.10 # To update, run: # - # pip-compile + # pip-compile --output-file=requirements.txt pyproject.toml # - asgiref==3.2.3 + + asgiref==3.5.2 + # via django + django==4.1 + # via my-cool-django-app (pyproject.toml) + sqlparse==0.4.2 # via django - django==3.0.3 - # via my_django_project (setup.py) - pytz==2019.3 + + $ pip-compile --extra dev -o dev-requirements.txt pyproject.toml + # + # This file is autogenerated by pip-compile with python 3.10 + # To update, run: + # + # pip-compile --extra=dev --output-file=dev-requirements.txt pyproject.toml + # + + asgiref==3.5.2 # via django - sqlparse==0.3.0 + attrs==22.1.0 + # via pytest + django==4.1 + # via my-cool-django-app (pyproject.toml) + iniconfig==1.1.1 + # via pytest + packaging==21.3 + # via pytest + pluggy==1.0.0 + # via pytest + py==1.11.0 + # via pytest + pyparsing==3.0.9 + # via packaging + pytest==7.1.2 + # via my-cool-django-app (pyproject.toml) + sqlparse==0.4.2 # via django + tomli==2.0.1 + # via pytest + +This is great for both pinning your applications, but also to keep the CI +of your open-source Python package stable. + +Requirements from ``setup.py`` and ``setup.cfg`` +------------------------------------------------ -``pip-compile`` will produce your ``requirements.txt``, with all the Django -dependencies (and all underlying dependencies) pinned. +``pip-compile`` has also full support for ``setup.py``- and +``setup.cfg``-based projects that use ``setuptools``. -Without ``setup.py`` --------------------- +Just define your dependencies and extras as usual and run +``pip-compile`` as above. -If you don't use ``setup.py`` (`it's easy to write one`_), you can create a -``requirements.in`` file to declare the Django dependency: +Requirements from ``requirements.in`` +------------------------------------- + +You can also use plain text files for your requirements (e.g. if you don't +want your application to be a package). To use a ``requirements.in`` file to +declare the Django dependency: .. code-block:: ini @@ -129,15 +196,13 @@ Now, run ``pip-compile requirements.in``: And it will produce your ``requirements.txt``, with all the Django dependencies (and all underlying dependencies) pinned. -.. _it's easy to write one: https://packaging.python.org/guides/distributing-packages-using-setuptools/#configuring-your-project - .. _Updating requirements: Updating requirements --------------------- ``pip-compile`` generates a ``requirements.txt`` file using the latest versions -that fulfil the dependencies of ``setup.py`` or ``requirements.in``. +that fulfil the dependencies you specify in the supported files. If ``pip-compile`` finds an existing ``requirements.txt`` file that fulfils the dependencies then no changes will be made, even if updates are available. diff --git a/piptools/scripts/compile.py b/piptools/scripts/compile.py index 28e16abf2..9424968ac 100755 --- a/piptools/scripts/compile.py +++ b/piptools/scripts/compile.py @@ -287,7 +287,10 @@ def cli( emit_options: bool, unsafe_package: Tuple[str, ...], ) -> None: - """Compiles requirements.txt from requirements.in specs.""" + """ + Compiles requirements.txt from requirements.in, pyproject.toml, setup.cfg, + or setup.py specs. + """ log.verbosity = verbose - quiet if len(src_files) == 0: