Skip to content

fix(dpmodel): move econf embeddings to active backend#5840

Open
njzjz-bot wants to merge 3 commits into
deepmodeling:masterfrom
njzjz-bot:fix/dpmodel-econf-type-embed-backend-5641
Open

fix(dpmodel): move econf embeddings to active backend#5840
njzjz-bot wants to merge 3 commits into
deepmodeling:masterfrom
njzjz-bot:fix/dpmodel-econf-type-embed-backend-5641

Conversation

@njzjz-bot

@njzjz-bot njzjz-bot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Fixes #5641

Summary

  • keep electronic-configuration tables as portable NumPy state for serialization
  • materialize the table at call time in the namespace, dtype, and device of the first embedding weight
  • prevent NativeLayer from selecting NumPy and coercing Torch/JAX/array-API weights back to CPU
  • cover tables regenerated by change_type_map() through the same call-time boundary

Why existing tests missed this

The cross-backend consistency tests already include electronic-configuration embeddings, but their JAX, array-api-strict, TF2, and exportable-PyTorch wrappers eagerly convert NumPy attributes when constructing the backend object. That converts both the weights and econf_tebd, so the generic dpmodel mixed-state boundary is never exercised.

The direct dpmodel path uses NumPy parameters and a NumPy electronic-configuration table, where NativeLayer selecting its namespace from the input is correct. Existing tests therefore compared homogeneous NumPy state or homogeneous wrapper-converted state, but never backend-native weights alongside the intentionally portable NumPy constant. CPU-only numerical comparisons also did not assert the returned array backend, dtype, or device.

Validation

  • source/tests/consistent/test_type_embedding.py: 64 passed, 49 backend-dependent skips
  • focused regression converts only dpmodel layer weights to Torch and verifies Torch output, dtype, device, and NumPy numerical parity
  • the same regression repeats after change_type_map() regenerates the NumPy electronic-configuration table
  • ruff format .
  • ruff check .

Coding agent: Codex
Codex version: codex-cli 0.144.4
Model: gpt-5.6-sol
Reasoning effort: xhigh

Summary by CodeRabbit

  • Bug Fixes

    • Electronic-configuration type embeddings now consistently render using the active backend, matching the sampled weights’ dtype and device.
    • Improved cross-backend correctness when mixing portable constants with PyTorch/JAX weights, including after type-map remapping.
  • Tests

    • Added a PyTorch-only consistency test covering electronic-configuration embedding behavior with NumPy-deserialized references.
    • Updated the JAX test to validate both electronic-configuration modes without relying on a single pre-built model.

Materialize portable NumPy electronic-configuration tables in the namespace, dtype, and device of the type-embedding weights before evaluation. This prevents NativeLayer from selecting NumPy and coercing backend-native parameters back to CPU.

Add a direct mixed-state regression covering Torch output identity, numerical parity, and change_type_map regeneration without relying on eager-converting backend wrappers.

Coding-Agent: Codex
Codex-Version: codex-cli 0.144.4
Model: gpt-5.6-sol
Reasoning-Effort: xhigh
@dosubot dosubot Bot added the bug label Jul 16, 2026
@coderabbitai

coderabbitai Bot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Warning

Review limit reached

@njzjz, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 39 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 32a81e7b-269a-41e8-a8ca-47f5ed38e4fd

📥 Commits

Reviewing files that changed from the base of the PR and between 8fd3097 and 1f3f7c4.

📒 Files selected for processing (1)
  • source/tests/jax/test_type_embed.py
📝 Walkthrough

Walkthrough

TypeEmbedNet.call() now converts electronic-configuration embeddings to the active backend, dtype, and device. Tests cover PyTorch parameter consistency, type-map remapping, and JAX tracing with both embedding configurations.

Changes

Electronic-configuration backend alignment

Layer / File(s) Summary
Call-time backend conversion and PyTorch validation
deepmd/dpmodel/utils/type_embed.py, source/tests/consistent/test_type_embedding.py
TypeEmbedNet.call() materializes electronic-configuration embeddings using the active weight’s dtype and device. The PyTorch test verifies output type, device, numerical equivalence, and remapping behavior.
JAX tracing coverage for both configurations
source/tests/jax/test_type_embed.py
The JAX test runs JIT and gradient checks with electronic-configuration embeddings enabled and disabled, validating output shape, gradients, and finite results.

Estimated code review effort: 2 (Simple) | ~10 minutes

Possibly related PRs

  • deepmodeling/deepmd-kit#5736: Both changes adjust TypeEmbedNet.call() to create backend-specific arrays with the appropriate dtype and device.
🚥 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 is concise and accurately describes the main change to move econf embeddings onto the active backend.
Linked Issues check ✅ Passed The code and tests implement #5641 by materializing econf tables on the active backend and adding regression coverage.
Out of Scope Changes check ✅ Passed The added JAX and mixed-state tests are directly related to the backend conversion fix and not unrelated scope.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
✨ 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.

@codecov

codecov Bot commented Jul 16, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 78.63%. Comparing base (6c3b985) to head (1f3f7c4).
⚠️ Report is 31 commits behind head on master.

Additional details and impacted files
@@            Coverage Diff             @@
##           master    #5840      +/-   ##
==========================================
+ Coverage   78.58%   78.63%   +0.04%     
==========================================
  Files        1050     1054       +4     
  Lines      120637   121758    +1121     
  Branches     4356     4406      +50     
==========================================
+ Hits        94801    95741     +940     
- Misses      24278    24444     +166     
- Partials     1558     1573      +15     

☔ 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 commented Jul 18, 2026

Copy link
Copy Markdown
Member

Possible reviewers based on changed lines, exact file history, and exact-file review history:

  • @OutisLi — 14 reviews on exact changed files (deepmd/dpmodel/utils/type_embed.py).
  • @iProzd — 6 commits on changed files (deepmd/dpmodel/utils/type_embed.py, source/tests/consistent/test_type_embedding.py).

No review request was made automatically.

Coding agent: Codex
Codex version: codex-cli 0.144.4
Model: gpt-5.6-sol
Reasoning effort: xhigh

@njzjz
njzjz requested review from OutisLi and iProzd and removed request for OutisLi and iProzd July 18, 2026 07:17

@wanghan-iapcm wanghan-iapcm left a comment

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.

The fix is correct and minimal — materializing econf_tebd onto the active backend at call time resolves the namespace-coercion, preserves the numpy storage for serialization, and (verified locally) also repairs the JAX nnx.jit/nnx.grad crash that use_econf_tebd=True hit before. One coverage note inline.

Comment thread deepmd/dpmodel/utils/type_embed.py
Exercise both one-hot and electronic-configuration type embeddings under nnx.jit and nnx.grad, including the type map required by the electronic path.

Coding-Agent: Codex
Codex-Version: codex-cli 0.144.6
Model: gpt-5.6-sol
Reasoning-Effort: xhigh

@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.

Actionable comments posted: 1

🤖 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.

Inline comments:
In `@source/tests/jax/test_type_embed.py`:
- Around line 41-44: Strengthen the gradient check in the test around forward
and grad by capturing the result of grad(type_embedding) and validating its
gradient leaves are finite and non-degenerate where applicable, rather than only
asserting the gradient state is non-null. Preserve the existing output-shape and
output-NaN checks.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 823f87e8-3fcc-4a1b-b2ff-0d54a1deb717

📥 Commits

Reviewing files that changed from the base of the PR and between a095055 and 8fd3097.

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

Comment thread source/tests/jax/test_type_embed.py
Assert that traced TypeEmbedNet gradient states contain finite, nonzero leaves for both one-hot and electronic-configuration embeddings.

Coding-Agent: Codex
Codex-Version: codex-cli 0.144.6
Model: gpt-5.6-sol
Reasoning-Effort: xhigh
@njzjz
njzjz requested a review from wanghan-iapcm July 24, 2026 15:07

@wanghan-iapcm wanghan-iapcm left a comment

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.

This closes the gap properly. Adding use_econf_tebd=True to the nnx.jit/nnx.grad test covers the real production path rather than a constructed one: before this, the only new test was torch-only and eager, and it manufactured a numpy-econf-beside-torch-weights state that no wrapper actually produces (pt_expt stores econf_tebd as a torch buffer, JAX as an ArrayAPIVariable), so it guarded the class rather than the failure.

That matters for whether this PR has a genuine regression test, and now it does. I reproduced the pre-fix crash locally - use_econf_tebd=True under nnx.jit threw DynamicJaxprTracer has no attribute device, the same pattern #5736 fixed for the sibling xp.eye branch - so the new subtest fails before the fix and passes after. The any(np.abs(leaf) > 0.0) assertion added in the follow-up is a good touch; it stops the test passing on a degenerate all-zero gradient.

One optional follow-up, not for this PR: change_type_map() still calls array_api_compat.device() directly instead of the tracing-safe _array_device_or_none() helper, which is now the last instance of that pattern in the file.

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.

[Code scan] Move electronic-configuration type embeddings onto the active backend

3 participants