Skip to content

[bug] moon docker setup installs only the last dependency's packages in Python/uv workspaces, ignoring the focused project #2381

@lucasmsoares96

Description

@lucasmsoares96

Describe the bug

When using moon docker setup inside a Dockerfile for a Python/uv workspace, the command runs uv venv + uv sync separately for each project in the dependency tree. Each iteration recreates the virtual environment from scratch, so only the last project's dependencies survive in the final .venv. The focused project's own dependencies are never installed.

For example, given a project python_bot that depends on a workspace package chatwoot_api:

# moon.yml (python_bot)
dependsOn:
  - chatwoot_api

The build log from moon docker setup shows:

▮▮▮▮ uv venv .venv --no-managed-python --no-python-downloads --no-progress
Using CPython 3.13.0 interpreter at: /root/.proto/tools/python/3.13.0/bin/python
Creating virtual environment at: .venv
▮▮▮▮ uv venv .venv --no-managed-python --no-python-downloads --no-progress
▮▮▮▮ uv sync --no-managed-python --no-python-downloads --no-progress
Using CPython 3.13.0 interpreter at: /root/.proto/tools/python/3.13.0/bin/python3
Creating virtual environment at: .venv          ← venv recreated, previous state lost
Resolved 220 packages in 1ms
Bytecode compiled 1 file in 318ms
Resolved 220 packages in 1ms
   Building chatwoot-api @ file:///app/backend/packages/chatwoot_api
▮▮▮▮ uv sync --no-managed-python --no-python-downloads --no-progress
Prepared 16 packages in 3.66s
Installed 16 packages in 81ms                   ← only chatwoot_api deps installed

uv sync resolves all 220 packages in the lockfile but only installs 16 — exactly chatwoot_api's dependency tree. The focused project (python_bot) has 25 dependencies (including debugpy, fastapi, uvicorn, etc.) and none of them are installed.

At runtime the container fails immediately:

/app/backend/.venv/bin/python: No module named debugpy

Steps to reproduce

  1. Create a uv workspace with a root pyproject.toml:

    [project]
    name = "backend"
    requires-python = ">=3.13"
    
    [tool.uv.workspace]
    members = ["apps/*", "packages/*"]
  2. Create an app (apps/my-app) with dependencies:

    [project]
    name = "my-app"
    dependencies = ["debugpy>=1.8.12", "fastapi[standard]>=0.115.5"]
  3. Create a workspace package (packages/my-lib) with its own dependencies:

    [project]
    name = "my-lib"
    dependencies = ["httpx>=0.28.1"]
  4. Set dependsOn: [my-lib] in apps/my-app/moon.yml.

  5. Configure toolchains.yml:

    unstable_python:
      version: 3.13.0
      packageManager: "uv"
    unstable_uv:
      version: "0.9"
  6. Build with this Dockerfile:

    FROM node:latest AS base
    WORKDIR /app
    RUN curl -fsSL https://moonrepo.dev/install/moon.sh | bash -s -- 2.0.1
    ENV PATH="/root/.moon/bin:/root/.proto/bin:$PATH"
    
    FROM base AS skeleton
    COPY . .
    RUN moon docker scaffold my-app-backend
    
    FROM base AS build
    COPY --from=skeleton /app/.moon/docker/configs .
    COPY --from=skeleton /app/.moon/docker/sources .
    RUN moon docker setup
    RUN moon docker prune
    
    FROM python:3.13-slim
    COPY --from=build /app /app
    CMD ["python", "-m", "my_app"]
  7. Run the image — it fails with No module named ... for any of my-app's dependencies.

Expected behavior

moon docker setup should install all dependencies for the focused project and its workspace dependencies into a single virtual environment. The uv venv command should only be called once, and uv sync should install the complete dependency tree for the focused project.

Ideally the setup step should run something equivalent to:

uv venv .venv --no-managed-python --no-python-downloads
uv sync --package my-app --no-managed-python --no-python-downloads

Environment

➜  python_bot git:(moon) ✗ pnpm dlx envinfo

  System:
    OS: Linux 6.17 Ubuntu 24.04.4 LTS 24.04.4 LTS (Noble Numbat)
    CPU: (8) x64 11th Gen Intel(R) Core(TM) i7-1165G7 @ 2.80GHz
    Memory: 5.91 GB / 15.35 GB
    Container: Yes
    Shell: 5.9 - /usr/bin/zsh
  Binaries:
    Node: 22.22.0 - /home/lucas/.proto/tools/node/22.22.0/bin/node
    npm: 10.9.4 - /home/lucas/.proto/tools/node/22.22.0/bin/npm
    pnpm: 10.28.1 - /home/lucas/.proto/tools/pnpm/10.28.1/shims/pnpm
    Watchman: 20251124.015248.0 - /usr/local/bin/watchman
  Managers:
    Apt: 2.8.3 - /usr/bin/apt
  Utilities:
    Git: 2.43.0 - /usr/bin/git
    FFmpeg: 6.1.1 - /usr/bin/ffmpeg
    Curl: 8.5.0 - /usr/bin/curl
    OpenSSL: 3.0.13 - /usr/bin/openssl
  Virtualization:
    Docker: 29.2.1 - /usr/bin/docker
  IDEs:
    Nano: 7.2 - /usr/bin/nano
    Claude Code: 2.1.39 - /home/lucas/.local/bin/claude
    opencode: 1.1.53 - /home/lucas/.opencode/bin/opencode
    Vim: 0.9.5 - /usr/bin/vim
  Languages:
    Bash: 5.2.21 - /usr/bin/bash
    Java: 21.0.10 - /usr/bin/javac
    Perl: 5.38.2 - /usr/bin/perl
    Python: 3.13.0 - /home/lucas/.proto/shims/python
    Python3: 3.12.3 - /usr/bin/python3
  Databases:
    SQLite: 3.44.4 - /home/lucas/Android/Sdk/platform-tools/sqlite3
  Browsers:
    Chrome: 145.0.7632.75
    Firefox: 147.0.4
    Firefox Developer Edition: 147.0.4

Additional context

  • This bug also occurs on moon 1.41.8 (pre-2.0 migration) — it is not a regression from the v2 upgrade.
  • The moon docker prune step (which runs in 0.6s and does nothing visible for Python) does not mitigate or worsen the issue. The packages are already missing after moon docker setup.
  • The root cause appears to be that moon iterates over each project in the dependency graph and runs uv venv + uv sync independently for each one, with each uv venv call wiping the previous environment.
  • Current workaround: add a manual uv sync step in the Dockerfile after moon docker setup:
    RUN moon docker setup
    WORKDIR /app/backend
    RUN /root/.proto/tools/uv/0.9.30/uv sync --package my-app --no-managed-python --no-python-downloads
    WORKDIR /app
    RUN moon docker prune

Metadata

Metadata

Assignees

Labels

bugSomething isn't working

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions