python-poetry / python-poetry/poetry

PEP-621 static dependencies lose `develop = true` on transitive dependencies

Open
#10,683 9 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

kind/bug status/triage
Dominant language
Python
Stars
34.3k
Forks
2.5k
Avg merge
2d 19h
Merged PRs (30d)
30

Description

Description

I have a form of monorepo - one repo containing multiple directories, each of which has its own Poetry config. Some of these packages depend on other packages in other sub-directories. Sometimes those chains can be three and four levels deep.

With the old pre-PEP-621 tool.poetry format in pyproject.toml then the develop flag persists into the lock file regardless of the depth of the chain. With a newer PEP-621 project format with the dependency defined in project.dependencies and the extra develop=true metadata set in tool.poetry.dependencies then the develop = true value is only retained for the directly referenced project and the transitive dependency loses its flag and goes back to develop = false.

This doesn't seem to cause issues while developing (e.g. running PyTest) because the site-packages uses a .pth file and so loads the current files. But it does cause issues during packaging and deployment (e.g. Serverless publishing to AWS) because the packaging process has cached the transitive dependency (because it's develop = false) and doesn't include any newer changes.

For example, given the projects base, lib and service with a dependency chain of service depends on lib and lib depends on base, where lib and service both add develop = true metadata to the dependency then the poetry.lock file for lib has develop = true on base and service has develop = true on lib, but service has develop = false on the transitive dependency to base and so won't include any changes made within the base project.

Comparative "new" and "old" format structures: poetry-bug.zip

Git-style diff between the two folders:

diff -Naur old-format/base/poetry.lock new-format/base/poetry.lock
--- old-format/base/poetry.lock 2026-01-08 14:24:13.102219878 +0000
+++ new-format/base/poetry.lock 2026-01-08 13:53:27.263624844 +0000
@@ -4,4 +4,4 @@
 [metadata]
 lock-version = "2.1"
 python-versions = ">=3.14"
-content-hash = "93de2bb2d66318c60f5f9a4b648ffe8bb54e5083b54f259834eb309d0214bd01"
+content-hash = "a17e7643ed4aefa81470391aa6cad48a796709c4f4bc8d4f3c99db84a3c428dd"
diff -Naur old-format/base/pyproject.toml new-format/base/pyproject.toml
--- old-format/base/pyproject.toml      2026-01-08 14:31:41.184379664 +0000
+++ new-format/base/pyproject.toml      2026-01-08 14:31:26.459476540 +0000
@@ -1,15 +1,14 @@
-[tool.poetry]
+[project]
 name = "base"
 version = "0.1.0"
 description = ""
 authors = [
-    "Your Name <you@example.com>"
+    {name = "Your Name",email = "you@example.com"}
 ]
 readme = "README.md"
-
-[tool.poetry.dependencies]
-python = ">=3.14"
-
+requires-python = ">=3.14"
+dependencies = [
+]
 
 [build-system]
 requires = ["poetry-core>=2.0.0,<3.0.0"]
diff -Naur old-format/lib/poetry.lock new-format/lib/poetry.lock
--- old-format/lib/poetry.lock  2026-01-08 14:28:02.893520718 +0000
+++ new-format/lib/poetry.lock  2026-01-08 13:53:27.271598654 +0000
@@ -17,4 +17,4 @@
 [metadata]
 lock-version = "2.1"
 python-versions = ">=3.14"
-content-hash = "ca97d18604dbe204d15864ccdfe479d491b1f91c121f85926a4964ca34d2fbf2"
+content-hash = "a7a987130a2aed489d429f4703948023dcf76d32148b58851c1fdfdb6a6f5aa5"
diff -Naur old-format/lib/pyproject.toml new-format/lib/pyproject.toml
--- old-format/lib/pyproject.toml       2026-01-08 14:27:51.621315144 +0000
+++ new-format/lib/pyproject.toml       2026-01-08 15:32:49.782545948 +0000
@@ -1,17 +1,19 @@
-[tool.poetry]
+[project]
 name = "lib"
 version = "0.1.0"
 description = ""
 authors = [
-    "Your Name <you@example.com>"
+    {name = "Your Name",email = "you@example.com"}
 ]
 readme = "README.md"
+requires-python = ">=3.14"
+dependencies = [
+    "base @ ../base"
+]
 
 [tool.poetry.dependencies]
-python = ">=3.14"
-base = { path = "../base", develop = true }
+base = { develop = true }
 
 [build-system]
 requires = ["poetry-core>=2.0.0,<3.0.0"]
 build-backend = "poetry.core.masonry.api"
-
diff -Naur old-format/service/poetry.lock new-format/service/poetry.lock
--- old-format/service/poetry.lock      2026-01-08 14:29:17.109423780 +0000
+++ new-format/service/poetry.lock      2026-01-08 15:33:13.015370439 +0000
@@ -8,7 +8,7 @@
 python-versions = ">=3.14"
 groups = ["main"]
 files = []
-develop = true
+develop = false
 
 [package.source]
 type = "directory"
@@ -25,7 +25,7 @@
 develop = true
 
 [package.dependencies]
-base = {path = "../base", develop = true}
+base = {path = "../base"}
 
 [package.source]
 type = "directory"
@@ -34,4 +34,4 @@
 [metadata]
 lock-version = "2.1"
 python-versions = ">=3.14"
-content-hash = "1b127ecc24d022cbfecf9e41fceb18f14bd479f937070f12fe08899bdcf8b820"
+content-hash = "5932f53d95c41fda537a7746fb78b8c4164d54820271877b9b8f8bd702c8ac2f"
diff -Naur old-format/service/pyproject.toml new-format/service/pyproject.toml
--- old-format/service/pyproject.toml   2026-01-08 14:29:10.685377762 +0000
+++ new-format/service/pyproject.toml   2026-01-08 15:32:46.577867184 +0000
@@ -1,15 +1,18 @@
-[tool.poetry]
+[project]
 name = "service"
 version = "0.1.0"
 description = ""
 authors = [
-    "Your Name <you@example.com>"
+    {name = "Your Name",email = "you@example.com"}
 ]
 readme = "README.md"
+requires-python = ">=3.14"
+dependencies = [
+    "lib @ ../lib"
+]
 
 [tool.poetry.dependencies]
-python = ">=3.14"
-lib = { path = "../lib", develop = true }
+lib = { develop = true }
 
 [build-system]
 requires = ["poetry-core>=2.0.0,<3.0.0"]

(Notice the changes in service/poetry.lock)

Workarounds

Keeping a pre-PEP-621 or PEP-621 dynamic setup without project.dependencies and still specify everything in tool.poetry.dependencies retains the old behaviour.

Duplicating the path in tool.poetry.dependencies definition (not just develop = true) doesn't appear to work.

Adding a develop=true dependency into tool.poetry.dependencies for every transitive dependency without specifying it in project.dependencies isn't scalable and doesn't seem to work.

Duplicating the transitive dependencies and putting them into tool.poetry.dependencies in the dependent project does appear to work but isn't scalable.

Poetry Installation Method

install.python-poetry.org

Operating System

Ubuntu 24.04 in WSL

Poetry Version

Poetry (version 2.2.1)

Poetry Configuration
cache-dir = "/home/sjbertram/.cache/pypoetry"
data-dir = "/home/sjbertram/.local/share/pypoetry"
installer.max-workers = null
installer.no-binary = null
installer.only-binary = null
installer.parallel = true
installer.re-resolve = true
keyring.enabled = true
python.installation-dir = "{data-dir}/python"  # /home/sjbertram/.local/share/pypoetry/python
requests.max-retries = 0
solver.lazy-wheel = true
system-git-client = false
virtualenvs.create = true
virtualenvs.in-project = true
virtualenvs.options.always-copy = false
virtualenvs.options.no-pip = false
virtualenvs.options.system-site-packages = false
virtualenvs.path = "{cache-dir}/virtualenvs"  # /home/sjbertram/.cache/pypoetry/virtualenvs
virtualenvs.prompt = "{project_name}-py{python_version}"
virtualenvs.use-poetry-python = false
Python Sysconfig
sysconfig.log
Paste the output of 'python -m sysconfig', over this line.
Example pyproject.toml
See attachment in description - requires multiple config files
Poetry Runtime Logs

N/A

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start with the attached old-format and new-format project directories, then compare the generated poetry.lock files against their pyproject.toml dependency declarations. Reproduce the three-level service, lib, and base chain and trace lock generation for directory dependencies. Done means the transitive base dependency retains develop = true under the PEP-621 setup.

Written by the indexing model from the issue text.

Assessment

Tech stack
python
Domain
build-system, tooling
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
50/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.