Skip to content

feat(pt_expt): full model #5244

Merged
wanghan-iapcm merged 74 commits intodeepmodeling:masterfrom
wanghan-iapcm:feat-full-model-1
Feb 16, 2026
Merged

feat(pt_expt): full model #5244
wanghan-iapcm merged 74 commits intodeepmodeling:masterfrom
wanghan-iapcm:feat-full-model-1

Conversation

@wanghan-iapcm
Copy link
Collaborator

@wanghan-iapcm wanghan-iapcm commented Feb 16, 2026

Summary by CodeRabbit

  • New Features

    • Added a PyTorch experimental energy model with exportable lower-level tracing, descriptor/accessor and output-definition APIs, and output-bias management.
  • Bug Fixes

    • Fixed device placement for created tensors and added runtime validations for several model accessors.
  • Tests

    • Expanded test suite with autodiff/derivative validation, export/tracing checks, and cross-backend API consistency tests.

Comment on lines +36 to +44
def forward(
self,
coord: torch.Tensor,
atype: torch.Tensor,
box: torch.Tensor | None = None,
fparam: torch.Tensor | None = None,
aparam: torch.Tensor | None = None,
do_atomic_virial: bool = False,
) -> dict[str, torch.Tensor]:

Check warning

Code scanning / CodeQL

Signature mismatch in overriding method Warning

This method requires at least 3 positional arguments, whereas overridden
Identity.forward
requires 2.
This method requires at least 3 positional arguments, whereas overridden test_torch_module_respects_explicit_forward.MockModule.forward requires 2.
return
return super().__setattr__(name, value)

def call(self, x: torch.Tensor) -> torch.Tensor:

Check warning

Code scanning / CodeQL

Signature mismatch in overriding method Warning

This method does not accept arbitrary keyword arguments, which overridden
NativeOP.call
does.
This call
correctly calls the base method, but does not match the signature of the overriding method.
This method requires 2 positional arguments, whereas overridden
NativeOP.call
may be called with 1.
This call
correctly calls the base method, but does not match the signature of the overriding method.
This method requires 2 positional arguments, whereas overridden
NativeOP.call
may be called with arbitrarily many.
This call
correctly calls the base method, but does not match the signature of the overriding method.
"energy": energy_data,
"find_energy": np.float32(1.0),
}
]

Check notice

Code scanning / CodeQL

Imprecise assert Note test

assertTrue(a > b) cannot provide an informative message. Using assertGreater(a, b) instead will give more informative messages.
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 16, 2026

📝 Walkthrough

Walkthrough

This PR adds a PyTorch-exportable backend (pt_expt) with model, fitting, and network utilities; refactors dpmodel casting helpers to private variants; adds output-bias management and a descriptor accessor; makes tensor/device handling and assignment changes in transform/utility code; and expands tests for pt_expt (autodiff, exportable tracing, cross-backend API checks).

Changes

Cohort / File(s) Summary
pt_expt Module Infrastructure
deepmd/pt_expt/atomic_model/dp_atomic_model.py, deepmd/pt_expt/fitting/ener_fitting.py, deepmd/pt_expt/fitting/invar_fitting.py
Apply @torch_module decorator and remove manual init/call/setattr boilerplate; classes rely on decorator/base behavior; invar_fitting adds a forward wrapper.
pt_expt Model Framework
deepmd/pt_expt/model/__init__.py, deepmd/pt_expt/model/ener_model.py, deepmd/pt_expt/model/make_model.py, deepmd/pt_expt/model/transform_output.py
Introduce EnergyModel, make_model factory, exportable lower-forward tracing, and transform_output utilities (autograd-based force/virial/hessian computation and atomic virial correction).
pt_expt Network Utilities
deepmd/pt_expt/utils/network.py
Add pure-PyTorch call path for NativeLayer (make_fx friendly), register parameters as torch.nn.Parameter, and _torch_activation helper for native activations.
dpmodel Output Bias & Casting
deepmd/dpmodel/model/make_model.py
Add get_out_bias, set_out_bias, change_out_bias; refactor input/output casting to _input_type_cast/_output_type_cast, add get_xp_precision usage and xp-aware casting, and wire aliases forward_common/forward_common_lower.
dpmodel Minor Fixes
deepmd/dpmodel/fitting/general_fitting.py, deepmd/dpmodel/model/transform_output.py, deepmd/dpmodel/utils/network.py
Accumulate outputs into a results dict in general_fitting; make tensor creation device-aware in transform_output; replace in-place arithmetic with assignments in network.NativeLayer.
dpmodel Model Accessors
deepmd/dpmodel/model/dp_model.py, deepmd/dpmodel/model/ener_model.py
Add DPModelCommon.get_descriptor and EnergyModel.translated_output_def to map internal output keys to user-facing outputs (conditional force/virial/hessian entries).
Paddle/PyTorch Casting Refactor
deepmd/pd/model/model/make_model.py, deepmd/pt/model/model/make_model.py
Rename input_type_cast/output_type_cast to _input_type_cast/_output_type_cast and update call sites to mark them private (no behavioral change).
PyTorch Accessor Validations
deepmd/pt/model/atomic_model/dp_atomic_model.py
Add runtime checks that raise when eval_descriptor or eval_fitting_last_layer caches are empty, failing fast with guidance.
Tests — Consistent & pt_expt
source/tests/consistent/model/common.py, source/tests/consistent/model/test_ener.py, source/tests/pt_expt/model/test_autodiff.py, source/tests/pt_expt/model/test_ener_model.py
Add pt_expt evaluation path and extensive tests: autodiff (force/virial finite-diff), exportable forward_lower tracing, cross-backend API parity tests, and EnergyModel unit tests verifying shapes/exports/dp-consistency.

Sequence Diagram(s)

sequenceDiagram
    participant App as Application
    participant EM as EnergyModel (pt_expt)
    participant CM as make_model.CM
    participant Atomic as AtomicModel
    participant Transform as transform_output.fit_output_to_model_output
    participant Autograd as torch.autograd

    App->>EM: forward(...)/forward_lower(...)
    EM->>CM: call / call_lower
    CM->>Atomic: forward_common_atomic (extended_coord, ...)
    Atomic-->>CM: fit_ret (atom energies etc.)
    CM->>Transform: fit_output_to_model_output(fit_ret, ...)
    Transform->>Autograd: compute gradients (forces/virial) if needed
    Autograd-->>Transform: derivative tensors
    Transform-->>CM: model-formatted outputs (energy, atom_energy, force, virial, ...)
    CM-->>EM: dict[str, Tensor]
    EM-->>App: return outputs
Loading
sequenceDiagram
    participant Dev as Developer/Test
    participant EM as EnergyModel
    participant Trace as torch.fx.make_fx
    participant Export as torch.export.export

    Dev->>EM: forward_lower_exportable(inputs)
    EM->>Trace: make_fx(_forward_lower) with grad enabled
    Trace-->>EM: traced Module
    Dev->>Export: torch.export.export(traced Module)
    Export-->>Dev: exportable artifact
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~75 minutes

Possibly related PRs

  • PR #5194: Closely related — implements/extends the PyTorch-exportable (pt_expt) backend and overlapping modules/classes.
  • PR #5213: Related — introduces/apply the torch_module decorator used across pt_expt classes in this PR.
  • PR #5207: Related — modifies pt_expt network wrappers (NativeLayer, parameter registration) with overlapping compatibility/tracing changes.

Suggested reviewers

  • njzjz
  • iProzd
🚥 Pre-merge checks | ✅ 3 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 61.90% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'feat(pt_expt): full model' directly describes the main objective of the PR—implementing full model support for the pt_expt module. While terse, it accurately conveys the primary change.
Merge Conflict Detection ✅ Passed ✅ No merge conflicts detected when merging into master

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Tip

Issue Planner is now in beta. Read the docs and try it out! Share your feedback on Discord.


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 and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

🧹 Nitpick comments (4)
source/tests/consistent/model/common.py (1)

110-121: Consider using a shared utility for tensor-to-numpy conversion.

The other eval methods (e.g., eval_pt_model) use dedicated conversion utilities (torch_to_numpy), while this method uses raw .detach().cpu().numpy(). For consistency, consider importing a pt_expt equivalent if one exists — or keep as-is since it's just test code.

The natoms parameter is unused but matches the interface contract of all sibling eval_*_model methods, so the static analysis warning is a false positive.

deepmd/pt_expt/model/ener_model.py (1)

120-171: Note: do_atomic_virial is baked into the traced module.

The do_atomic_virial flag is captured in the closure (line 166) and becomes a constant in the make_fx-traced module. This is documented in the docstring and appears intentional, but callers should be aware that a separate trace is needed for each value of do_atomic_virial.

deepmd/pt_expt/model/transform_output.py (1)

107-110: Consider adding strict=True to the zip call.

split_vv1 and split_svv1 are guaranteed to have the same length (both split with [1] * size), so this is safe. However, adding strict=True provides a defensive check and silences the Ruff B905 warning.

Proposed fix
-    for vvi, svvi in zip(split_vv1, split_svv1):
+    for vvi, svvi in zip(split_vv1, split_svv1, strict=True):
source/tests/consistent/model/test_ener.py (1)

137-138: Inconsistent guard: PT_EXPT checks pt_expt_class is not None but other backends don't.

Lines 133–134 for PT only check self.skip_pt, while PT_EXPT additionally checks self.pt_expt_class is not None. This is defensive and harmless, but the inconsistency is worth noting. If INSTALLED_PT_EXPT is True, EnergyModelPTExpt should never be None.

Copy link

@chatgpt-codex-connector chatgpt-codex-connector bot left a comment

Choose a reason for hiding this comment

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

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 7e51e9d4fb

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

🧹 Nitpick comments (1)
deepmd/pt_expt/model/ener_model.py (1)

148-167: self and do_atomic_virial are captured by the closure — both become constants in the traced graph.

This is fine for single-configuration export, but worth documenting explicitly:

  • do_atomic_virial (bool) is resolved statically during tracing — the exported module will always (or never) produce virial outputs, depending on the value passed here.
  • model = self means the traced graph inlines all model parameters. Any parameter updates after tracing won't be reflected.

If this is the intended contract, a brief inline comment on lines 148 and 166-167 noting this would save future readers from wondering.

@njzjz njzjz linked an issue Feb 16, 2026 that may be closed by this pull request
@codecov
Copy link

codecov bot commented Feb 16, 2026

Codecov Report

❌ Patch coverage is 93.20755% with 18 lines in your changes missing coverage. Please review.
✅ Project coverage is 82.16%. Comparing base (a0bd530) to head (3600076).
⚠️ Report is 1 commits behind head on master.

Files with missing lines Patch % Lines
deepmd/pt_expt/utils/network.py 75.75% 8 Missing ⚠️
deepmd/pt_expt/model/transform_output.py 93.90% 5 Missing ⚠️
deepmd/dpmodel/model/ener_model.py 93.75% 1 Missing ⚠️
deepmd/dpmodel/model/make_model.py 96.55% 1 Missing ⚠️
deepmd/pd/model/model/ener_model.py 0.00% 1 Missing ⚠️
deepmd/pt_expt/model/ener_model.py 97.91% 1 Missing ⚠️
deepmd/pt_expt/model/make_model.py 93.75% 1 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##           master    #5244      +/-   ##
==========================================
+ Coverage   82.12%   82.16%   +0.03%     
==========================================
  Files         736      740       +4     
  Lines       74237    74420     +183     
  Branches     3615     3616       +1     
==========================================
+ Hits        60966    61144     +178     
- Misses      12107    12114       +7     
+ Partials     1164     1162       -2     

☔ View full report in Codecov by Sentry.
📢 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.

@wanghan-iapcm wanghan-iapcm added this pull request to the merge queue Feb 16, 2026
Merged via the queue into deepmodeling:master with commit c337dea Feb 16, 2026
69 checks passed
@wanghan-iapcm wanghan-iapcm deleted the feat-full-model-1 branch February 16, 2026 19:08
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.

Full Model and Autograd Support (PyTorch Exportable)

3 participants