Skip to content

feat(lammps): load installed backends dynamically#5707

Open
njzjz wants to merge 2 commits into
deepmodeling:masterfrom
njzjz:feat/lammps-dynamic-backends
Open

feat(lammps): load installed backends dynamically#5707
njzjz wants to merge 2 commits into
deepmodeling:masterfrom
njzjz:feat/lammps-dynamic-backends

Conversation

@njzjz

@njzjz njzjz commented Jul 1, 2026

Copy link
Copy Markdown
Member

Summary

  • avoid importing TensorFlow and PyTorch unconditionally from deepmd.lmp
  • add runtime library paths only for installed TensorFlow and/or PyTorch backends, while preserving CUDA preload and TF<2.12 libpython preload behavior
  • update the pip install docs and add focused tests for missing-backend handling

Tests

  • PYTHONPATH=$PWD pytest source/tests/test_lmp.py -v
  • ruff check .
  • ruff format . / commit hook ruff format
  • git diff --check
  • fork CI on njzjz/deepmd-kit branch feat/lammps-dynamic-backends: Build C library, Build C++, Build/upload to PyPI, CodeQL, Test Python, and Test C++ all passed; Mirror skipped

Fork CI runs:

Summary by CodeRabbit

  • New Features
    • Improved automatic runtime detection for LAMMPS so it can load available TensorFlow and/or PyTorch libraries more reliably at startup.
  • Bug Fixes
    • Better handles systems where one or more backends are missing, avoiding failed or incomplete environment setup.
    • Improves compatibility with older TensorFlow installs by automatically locating required Python library components.
  • Documentation
    • Clarified pip extras guidance for LAMMPS/i-PI, updating backend requirements wording.
  • Tests
    • Added Linux/macOS-only coverage to validate library-path discovery and LAMMPS environment configuration.

Copilot AI review requested due to automatic review settings July 1, 2026 23:47

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@coderabbitai

coderabbitai Bot commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

The PR refactors deepmd/lmp.py into helper-based TensorFlow/PyTorch library-path discovery and LAMMPS environment setup, adds tests for the new control flow, and updates installation documentation.

Changes

LAMMPS environment refactor

Layer / File(s) Summary
Import cleanup and library path helper functions
deepmd/lmp.py
Removes top-level TF/PyTorch imports, adds Version/SHARED_LIB_DIR imports, and introduces helper functions that conditionally import TensorFlow/PyTorch and return their library/preload paths, returning empty results when a backend is unavailable.
Environment configuration function and execution
deepmd/lmp.py
Replaces inline setup with _configure_lammps_environment(), which aggregates CUDA/TF/PyTorch paths, sets preload_env/lib_env via get_env, defines op_dir, and runs at import time.
Tests and documentation updates
source/tests/test_lmp.py, doc/install/easy-install.md
Adds platform-gated tests covering helper discovery and _configure_lammps_environment() under missing/present backend scenarios; updates docs to state LAMMPS dynamically loads installed TensorFlow/PyTorch and mentions JAX.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Sequence Diagram(s)

sequenceDiagram
  participant lmp as deepmd/lmp.py (import time)
  participant tfHelper as _get_tensorflow_library_paths
  participant ptHelper as _get_pytorch_library_paths
  participant env as os.environ

  lmp->>tfHelper: get TF lib/preload paths
  tfHelper-->>lmp: paths or empty (if TF missing)
  lmp->>ptHelper: get PyTorch lib path
  ptHelper-->>lmp: path or empty (if torch missing)
  lmp->>lmp: compute CUDA paths (Linux)
  lmp->>env: set preload_env via get_env
  lmp->>env: set lib_env via get_env
Loading

Suggested labels: LAMMPS

Suggested reviewers: wanghan-iapcm

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately summarizes the main change: LAMMPS now loads installed backends dynamically at runtime.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (1)
source/tests/test_lmp.py (1)

33-54: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Consider adding a test for the TF ≥ 2.12 branch.

Current coverage only exercises the TF_VERSION < 2.12 path (libpython preload). Add a complementary test with TF_VERSION="2.12.0" (or later) asserting the preload list stays empty, to guard the version-gated branch in _get_tensorflow_library_paths against regressions.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@source/tests/test_lmp.py` around lines 33 - 54, Add a complementary test for
the TF_VERSION >= 2.12 branch in _get_tensorflow_library_paths, similar to
test_tensorflow_library_paths_include_libpython_for_old_tensorflow. Mock
deepmd.tf.env with TF_VERSION set to 2.12.0 or later and assert the returned
TensorFlow library paths are still correct while the libpython preload list is
empty, ensuring the version-gated logic does not regress.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Nitpick comments:
In `@source/tests/test_lmp.py`:
- Around line 33-54: Add a complementary test for the TF_VERSION >= 2.12 branch
in _get_tensorflow_library_paths, similar to
test_tensorflow_library_paths_include_libpython_for_old_tensorflow. Mock
deepmd.tf.env with TF_VERSION set to 2.12.0 or later and assert the returned
TensorFlow library paths are still correct while the libpython preload list is
empty, ensuring the version-gated logic does not regress.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: 256487fb-b134-4331-9a78-ff4abb1c8d12

📥 Commits

Reviewing files that changed from the base of the PR and between 42de67e and 81d8828.

📒 Files selected for processing (3)
  • deepmd/lmp.py
  • doc/install/easy-install.md
  • source/tests/test_lmp.py

@codecov

codecov Bot commented Jul 2, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 81.19%. Comparing base (42de67e) to head (4a4995b).
⚠️ Report is 14 commits behind head on master.

Additional details and impacted files
@@            Coverage Diff             @@
##           master    #5707      +/-   ##
==========================================
- Coverage   81.22%   81.19%   -0.04%     
==========================================
  Files         980      990      +10     
  Lines      109352   111035    +1683     
  Branches     4205     4232      +27     
==========================================
+ Hits        88821    90153    +1332     
- Misses      19011    19355     +344     
- Partials     1520     1527       +7     

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@njzjz njzjz requested a review from wanghan-iapcm July 2, 2026 05:18
Comment thread deepmd/lmp.py
Comment on lines +51 to +78
def _get_tensorflow_library_paths() -> tuple[list[str], list[str]]:
"""Get TensorFlow library and preload paths when TensorFlow is installed."""
try:
tf_env = import_module("deepmd.tf.env")
except ModuleNotFoundError as exc:
if exc.name == "tensorflow":
return [], []
raise

tf_dir = tf_env.tf.sysconfig.get_lib()
preload_paths = []
if Version(tf_env.TF_VERSION) < Version("2.12"):
find_libpython = import_module("find_libpython").find_libpython
libpython = find_libpython()
if libpython is not None:
preload_paths.append(libpython)
return [tf_dir, os.path.join(tf_dir, "python")], preload_paths


def _get_pytorch_library_paths() -> list[str]:
"""Get PyTorch library paths when PyTorch is installed."""
try:
torch = import_module("torch")
except ModuleNotFoundError as exc:
if exc.name == "torch":
return []
raise
return [os.path.join(torch.__path__[0], "lib")]

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Non-blocking (test coverage): source/tests/test_lmp.py is a welcome addition, but a few reachable branches of these new helpers aren't exercised. _get_tensorflow_library_paths is only tested with TF 2.11.0, so the TF >= 2.12 path (no libpython preload) and the find_libpython() is None case are untested; _get_pytorch_library_paths's success path (torch installed -> [torch/lib]) is never run because the _configure_lammps_environment tests monkeypatch the helper and the only direct torch test covers the missing-torch case; and the exc.name != "tensorflow"/"torch" re-raise branches (which intentionally propagate unrelated import errors) have no coverage. A couple of small cases would close these.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Addressed in 4a4995b by adding coverage for the TF >= 2.12 no-libpython-preload path, the TF < 2.12 find_libpython() is None path, the installed PyTorch library path, and the unrelated ModuleNotFoundError re-raise branches. Validated with venv/bin/python -m pytest source/tests/test_lmp.py -q and venv/bin/ruff check . --exclude venv.

@njzjz njzjz requested a review from wanghan-iapcm July 5, 2026 11:47

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (1)
source/tests/test_lmp.py (1)

57-154: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Optional: extract a shared import_module fake/fixture.

The fake_import_module closure with an AssertionError fallback for unexpected imports is repeated near-identically across these five tests. A small parametrized helper (e.g., mapping module_name -> return value or exception) would reduce duplication, but current tests are correct and readable as-is.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@source/tests/test_lmp.py` around lines 57 - 154, The five tests repeat the
same `fake_import_module` pattern with only the module-specific return/raise
behavior changing. Extract a shared helper or fixture around
`fake_import_module` used by `_get_tensorflow_library_paths()` and
`_get_pytorch_library_paths()`, ideally driven by a module-name-to-result
mapping, so the tests stay concise while preserving the current `AssertionError`
fallback for unexpected imports.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Nitpick comments:
In `@source/tests/test_lmp.py`:
- Around line 57-154: The five tests repeat the same `fake_import_module`
pattern with only the module-specific return/raise behavior changing. Extract a
shared helper or fixture around `fake_import_module` used by
`_get_tensorflow_library_paths()` and `_get_pytorch_library_paths()`, ideally
driven by a module-name-to-result mapping, so the tests stay concise while
preserving the current `AssertionError` fallback for unexpected imports.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: 38afed2c-fb79-4c84-9767-372c267b9b92

📥 Commits

Reviewing files that changed from the base of the PR and between 81d8828 and 4a4995b.

📒 Files selected for processing (1)
  • source/tests/test_lmp.py

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants