Phase 1 notes – the install_requires audit (2026-09-25)¶
Method¶
Two passes, which agreed.
Static. For every package checkout in the workspace, parse all
importstatements (ast), map each top-level module to its distribution, and compare against the declared requirements (requirements.txt/setup.cfg/setup.py/pyproject). Then discount anything in the transitive closure of the declared requirements (computed from installed metadata), and label each remaining import as unconditional, function-local, or try-guarded. Scripts:audit_requires.pyandaudit_refine.py(session scratchpad; ~120 lines, easy to recreate from this description).Empirical. For each core package,
uv venv+uv pip install <package>alone, then import every submodule (pkgutil.walk_packages).
Core packages¶
Empirical result (clean venv, package alone):
Package |
Result |
|---|---|
molsystem |
import fails: No module named ‘openbabel’ |
seamm |
fails the same way (via molsystem) |
seamm-exec |
fails the same way (via molsystem) |
seamm-util |
OK |
seamm-widgets |
OK (basis_set_exchange is a lazy import; see below) |
seamm-datastore |
OK at import; alembic needed for migrations (see below) |
seamm-ff-util |
OK |
reference-handler |
OK |
seamm-jobserver |
OK |
seamm-installer |
OK |
Fixes applied (one PR each):
molsystem: declare
openbabel>=3.1.1; replace the stale comment saying openbabel has no wheels. This single change closes the gap for everything downstream.seamm-datastore: declare
alembic–database/alembic/env.pyand the migration scripts import it, andseamm-installerruns them.seamm-widgets: declare
basis_set_exchange– imported inside the BSE picker (lazy, so import-time is unaffected, but the dependency is real). Added to the CI env’s pip sublist too.seamm: drop
seamm-datastore– nothing underseamm/imports it (seamm_dashboard_clientandreference_handlerare imported and stay).seamm-ff-util: declare
rdkit, whichff_assigner.pyandforcefield.pyimport directly (it arrived transitively via molsystem).
Plug-ins: genuine gaps, deferred to each plug-in’s next release¶
Real direct imports with no declaration and not in the transitive closure.
All are masked today because the installer installs every package; they
only bite on a standalone pip install <plug-in>.
Missing requirement |
Plug-ins |
|---|---|
openbabel |
gaussian, psi4, quickmin, read_structure (moot once molsystem declares it, but a direct import is a direct dependency) |
seamm-exec |
mopac, psi4 |
tabulate |
fhi_aims, thermomechanical, xtb |
seamm-thermochemistry |
gaussian (function-local import in |
model-chemistry-step |
lammps (function-local; needed for QM-MD over MDI) |
seamm-installer is imported by the installer.py of nine plug-ins
(atomic_charges, dftbplus, lammps, mopac, orca, packmol, psi4, xtb,
seamm-thermochemistry). That is not a requirements fix but a Phase 3
design constraint: those modules run inside the SEAMM venv as the
<pkg>-step-installer console scripts, so seamm-installer must stay
installed in the venv even when the CLI also lives in a uv tool
environment (or installer_base moves to a small shared library).
Discounted as false positives¶
try-guarded optional paths:
openeye(molsystem),mdi/mopactools/mpi4py/tblite(the MDI engines, which run in their own conda environments),xmltodict(dftbplus),openpyxl(seamm-thermochemistry importers),seamm_dashboard(datastore).Python 2 fallbacks in
seamm_util/printing.py(ConfigParser,thread); harmless, could be deleted.seamm_util/seamm_json.pyimportsseamminside a function: a deliberate inversion to avoid a cycle;seammis always present.seamm_webuideclares everything; the static parser misread itspyproject.toml.Unreleased / experimental checkouts (conformer_search, data_sources, pyscf, training_set_analysis, trajectory_analysis,
*_sv,old/) were scanned but are out of scope.
Also found on the way¶
seamm_installer/conda/meta.yamllistsopenbabelandrdkitas run dependencies the installer never imports (they were there to seed the bootstrap environment). Goes away with the feedstock.seamm_util’skaleidodependency is declared in the packaging metadata’s side-table only;seamm_utilitself does not import kaleido (plotly calls it for static image export), so it belongs inseamm_util’s requirements as a runtime-optional companion of plotly rather than in the side-table. Left for the seamm_util release that removes the side-table (Phase 2).
Phase 1b – CI on uv: pilot results (2026-09-25)¶
devops branch uv-ci (two commits) adds the uv path to CI,
BranchCI, Docs and Release, chosen per step by
hashFiles('devtools/conda-envs/test_env.yaml'). Pilot branches
ci-uv on seamm_widgets and molsystem delete the env file and carry a
temporary PilotCI.yaml that runs the full matrix from the devops branch.
First attempt failed on tkinter.
astral-sh/setup-uvwith apython-versioninput resolved to the runner’s system/usr/bin/python3.12, which has no tkinter, so seamm_widgets’ docs build died importing the package. Fix: the interpreter now comes fromactions/setup-python(toolcache builds include tkinter on ubuntu and macOS) and uv is only the installer,uv venv --seed --python "$(which python)".seamm_widgets: green across the matrix (ubuntu + macOS, 3.11 + 3.12). Lint & docs 18 s; each test job 20-35 s wall clock including environment creation. The conda path’s jobs on the same package take several minutes.
molsystem: lint, docs and the wheels are fine; one test job failed on five PubChem lookups (
No 3-D structure available for ammoniaand the like) that the conda-path CI on the same code passed minutes earlier and that a previous uv-path run also passed. PubChem throttling, not the workflow; re-run pending. Those tests should probably carry a network marker with a retry, independent of this campaign.uvsilently accepts extras a package does not define, so the workflow’s'.[test,docs]'is safe everywhere.References to
test_env.yamlthat need updating after the devops merge: the plug-in cookiecutter template (devtools/conda-envs/test_env.yamlanddevtools/README.md), therelease-seamm-pluginskill (SKILL.mdandcheck_deps.py), and seamm_dashboard’s Makefile (retiring anyway).
Outcome (later on 2026-09-25): devops PR #1 merged; the two ci-uv pilot
branches deleted; the plug-in cookiecutter template lost its devtools
directory (all conda-CI boilerplate); the release-seamm-plugin skill now
tells a release to git rm the env file, and check_deps.py exits
quietly without it. The five core packages with open PRs were converted by
deleting test_env.yaml: molsystem, seamm_widgets and seamm_datastore went
green at once; seamm and seamm_ff_util fail their docs build on
``No module named ‘openbabel’`` because they resolve molsystem from
PyPI, where 2026.9.20 still does not declare it. That is the audit’s core
finding biting for real, and it fixes the merge order: molsystem #119 first,
release, then re-run the other two. It also shows what the uv CI now
guarantees – a dependency gap anywhere in the chain fails the build the
same day.