From 7018a08e6a97e1b4fb02343a36160bb45e7495ee Mon Sep 17 00:00:00 2001 From: saileshwar-skyflow Date: Wed, 16 Sep 2026 17:25:53 +0530 Subject: [PATCH 1/3] SK-3118: Restore python-dotenv dependency for flowvault MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The bundled common/ module (common/utils/_utils.py) imports `dotenv`, so `python-dotenv` is a runtime dependency of the flowvault wheel. It was dropped during the bulk removal on the mistaken belief that only the deleted utils/_batching.py used it — but common is vendored into the wheel and needs it. As a result a clean `pip install skyflow-flowvault-python` fails at `import skyflow` with `ModuleNotFoundError: No module named 'dotenv'`. Re-add `python-dotenv >= 1.1.0, < 2` (matching skyvault, which kept it). Verified: the rebuilt wheel declares the dep, and a clean-venv install imports `skyflow` successfully. Co-Authored-By: Claude Opus 4.8 --- flowvault/setup.py | 1 + 1 file changed, 1 insertion(+) diff --git a/flowvault/setup.py b/flowvault/setup.py index 6dd86cf..f9d4a0a 100644 --- a/flowvault/setup.py +++ b/flowvault/setup.py @@ -89,6 +89,7 @@ def run(self): 'PyJWT >= 2.12, < 3', 'cryptography >= 44.0.2', 'httpx >= 0.21.2', + 'python-dotenv >= 1.1.0, < 2', # NOTE: 'requests' intentionally omitted -- only used today by v2's Connection # controller, which isn't part of v3's scope this round. ], From d20eba7b765d0998c3f5a8fdc40a3db1e0c326ed Mon Sep 17 00:00:00 2001 From: saileshwar-skyflow Date: Wed, 16 Sep 2026 17:31:13 +0530 Subject: [PATCH 2/3] SK-3118: Add clean-install smoke test to flowvault PR CI Build the wheel, install ONLY that wheel into a fresh virtualenv, and import skyflow from outside the repo. The venv has just the wheel's declared runtime dependencies, so a dependency missing from setup.py (like the python-dotenv drop that broke 1.0.0) fails the import here. The existing unit-test job installs dev deps, which masked this class of bug. Co-Authored-By: Claude Opus 4.8 --- .github/workflows/pr-flowvault.yml | 30 ++++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+) diff --git a/.github/workflows/pr-flowvault.yml b/.github/workflows/pr-flowvault.yml index 0ff1241..5b44ed3 100644 --- a/.github/workflows/pr-flowvault.yml +++ b/.github/workflows/pr-flowvault.yml @@ -82,3 +82,33 @@ jobs: flags: flowvault name: codecov-skyflow-python-flowvault verbose: true + + smoke: + name: Clean-install smoke test + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-python@v2 + with: + python-version: '3.9' + + # Build the wheel (it bundles the sibling common/ tree via setup.py's + # custom build_py), then install ONLY that wheel into a fresh virtualenv + # and import it. The venv contains just the wheel's declared runtime + # dependencies, so a dependency missing from setup.py fails the import + # here -- the unit-test job installs dev deps and would mask it. + - name: Build the flowvault wheel + run: | + python -m pip install --upgrade pip setuptools wheel + cd flowvault + python setup.py bdist_wheel + + - name: Install the wheel in a clean venv and import + run: | + python -m venv /tmp/smoke + /tmp/smoke/bin/pip install --upgrade pip + /tmp/smoke/bin/pip install flowvault/dist/*.whl + # Import from outside the repo so the source tree (flowvault/skyflow, + # ./common) is not on sys.path -- this exercises the installed wheel. + cd /tmp + /tmp/smoke/bin/python -c "import skyflow, common; from skyflow import Skyflow, Env, LogLevel; from skyflow.vault.data import InsertRequest, GetRequest, UpdateRequest, DeleteRequest, DetokenizeRequest, InsertOptions, GetOptions, UpdateOptions, DeleteOptions, DetokenizeOptions; from skyflow.vault.controller import VaultController; print('clean-install import OK')" From 309318f9d4b7321a2c5a3755f2c39f5d18d15802 Mon Sep 17 00:00:00 2001 From: saileshwar-skyflow Date: Wed, 16 Sep 2026 17:35:32 +0530 Subject: [PATCH 3/3] SK-3118: Gate release publish on a clean-install smoke test MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Before publishing to PyPI or JFrog (and even on a dry run), install each freshly built artifact — wheel and sdist — into its own clean virtualenv and import it from outside the repo. A missing runtime dependency in setup.py or a non-self-contained sdist now fails the release job before anything is uploaded, instead of shipping a broken artifact (as happened with 1.0.0's dropped python-dotenv). Applies to both skyvault and flowvault releases. Co-Authored-By: Claude Opus 4.8 --- .github/workflows/shared-build-and-deploy.yml | 22 +++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/.github/workflows/shared-build-and-deploy.yml b/.github/workflows/shared-build-and-deploy.yml index 7b142de..4bbcab5 100644 --- a/.github/workflows/shared-build-and-deploy.yml +++ b/.github/workflows/shared-build-and-deploy.yml @@ -123,6 +123,28 @@ jobs: cd "$MODULE" python setup.py sdist bdist_wheel + # Gate: install each freshly built artifact into its own clean virtualenv + # (only the package's DECLARED runtime deps present) and import it from + # outside the repo. This runs before either publish step and even on a + # dry run, so a missing runtime dependency in setup.py or a + # non-self-contained sdist fails here rather than shipping a broken + # release (both packages import as `skyflow` and bundle `common`). + - name: Smoke test the built package (clean install + import) + run: | + set -e + WHEEL=$(ls "$MODULE"/dist/*.whl) + SDIST=$(ls "$MODULE"/dist/*.tar.gz) + + python -m venv /tmp/smoke-wheel + /tmp/smoke-wheel/bin/pip install --upgrade pip + /tmp/smoke-wheel/bin/pip install "$WHEEL" + (cd /tmp && /tmp/smoke-wheel/bin/python -c "import skyflow, common; from skyflow import Skyflow, Env, LogLevel; print('wheel clean-install import OK')") + + python -m venv /tmp/smoke-sdist + /tmp/smoke-sdist/bin/pip install --upgrade pip setuptools wheel + /tmp/smoke-sdist/bin/pip install "$SDIST" + (cd /tmp && /tmp/smoke-sdist/bin/python -c "import skyflow, common; from skyflow import Skyflow, Env, LogLevel; print('sdist clean-install import OK')") + - name: Publish to PyPI if: ${{ (inputs.tag == 'beta' || inputs.tag == 'public') && inputs.dry-run != true }} env: