Repository navigation
Simplify and strengthen asset tests across physics backends - #7282
Conversation
|
There was a problem hiding this comment.
Isaac Lab Review Bot
The asset-test redesign establishes shared contracts, backend-focused units, and small real-solver seams, with accompanying PhysX and OVPhysX fixes. Before merge, remove the committed benchmark/work-report artifact and eliminate the redundant, unenforced public-member snapshots.
- Design and architecture: The contract/unit/integration ownership split and explicit backend-capability table are coherent. However, the committed redesign-results document is a machine- and revision-specific work artifact prohibited by repository guidance, and
public_surface.pycontains unused duplicate member inventories that can silently diverge from the enforced mappings. - API: The touched production APIs retain their signatures: PhysX collection COM/inertia changes reshape only at the TensorAPI boundary, deformable type inference preserves material-before-topology precedence, and the OVPhysX device lifecycle change affects internal manager behavior. The public-surface audit is useful, but its unused duplicate snapshots should be removed or made authoritative.
- Implementation: The contract bootstrap, backend capability declarations, manager patch scoping, writer readbacks, fused-layout checks, and backend regression seams were traced. Required cleanup is limited to removing the generated benchmark report from the repository and consolidating the duplicated public-member inventory.
Minor fixes needed. Posted 2 actionable findings inline.
Automated review; human maintainers own approval decisions.
| - Times in the comparison are the repository orchestrator's aggregate pytest | ||
| and subprocess wall times, not the outer shell duration. | ||
|
|
||
| ## Copy-ready PR performance section |
There was a problem hiding this comment.
🟡 Warning · Design Architecture — Committed generated benchmark results artifact
This file is a generated work report: it contains a "Copy-ready PR performance section", a rebase-specific base SHA, a machine-specific environment (GPU, driver, wheel versions), sandbox paths such as /tmp/isaaclab-task8-warp, and a per-module disposition map. Repository guidelines prohibit committing generated plans, scratch files, or agent artifacts. It will go stale immediately after merge and carries no reader-facing documentation value. Keep these measurements in the pull-request description instead.
|
|
||
|
|
||
| _PUBLIC_MEMBER_SNAPSHOT = { | ||
| "AssetBase": """ |
There was a problem hiding this comment.
🔵 Suggestion · Design Architecture — Unused member snapshots duplicate enforced mapping
Only the BaseRigidObjectData, BaseRigidObjectCollectionData, and BaseArticulationData entries of _PUBLIC_MEMBER_SNAPSHOT feed PUBLIC_SURFACE_CONTRACTS; the AssetBase, BaseRigidObject, BaseRigidObjectCollection, and BaseArticulation entries are never referenced and respell the same member names that the _mapping(...) calls list inline. A future API change updates only the audited copy, leaving a silently diverging second inventory. Drop the unreferenced entries or build the mappings from them.
e828d86 to
f2ab714
Compare
RigidObjectCollection.set_coms_index passed wp.transformf data to the PhysX tensor API, which raises a KeyError. It also marked the lazily filled body_com_pose_b cache as fresh after a partial write, so the unselected entries read back as zeros when the cache had not been read before. set_inertias_index flattened the (num_instances, num_bodies, 9) inertias with the 2D reshape, which the backend rejects. Pass the COM poses as float32, let the next read refresh the COM cache from the view as RigidObject does, and reshape the inertias with the 3D helper. A new test writes both properties to a non-sorted subset of (env, body) cells and checks the PhysX view and the data buffers.
Move the mocked cross-backend asset interface tests into a contract package with api, data, and write entry modules. An explicit capability table gives every backend a visible row: unavailable backends and unsupported branches collect as skips with their reason instead of silently dropping out. A kitless usdrt/carb stub and an availability guard keep PhysX articulations in the matrix, where they previously were skipped without notice. Factory manager patches are scoped to one test and restored afterwards. PhysX views apply TensorAPI writes so partial writers are checked against unselected backend rows, Newton joins the fixed-tendon contract, the deprecated command aliases are checked against the actuator collection, and one enforced inventory classifies the public base-class surface.
Replace the randomized and device-parametrized composer matrix with literal two-environment, two-body cases that pin frames, fast paths, live CoM and rotation reads, selection, set, reset, merge, lazy composition, and the deprecated API. Keep one real PhysX test: a world force at a world offset must match raw PhysX delivery, and a world wrench at the CoM of a rotated body far from the origin must follow the world axes. The composer-versus-PhysX matrix is removed; its only non-trivial parity case is the retained offset force, and its other cases issued the same PhysX call on both sides.
OvPhysxManager pinned the first simulation device for the whole process because the backend entered the OVPhysX process-wide CPU-only mode, which OVPhysX 0.6.3 still documents as irreversible. CPU scenes now leave that mode off and select CPU dynamics per scene through enableGPUDynamics=false and the MBP broadphase, as the OVPhysX developer guide recommends for mixed CPU/GPU processes, so the device lock is removed. A child-process test runs CPU, CUDA, CPU and CUDA, CPU scene sequences and checks device placement, state I/O, and that each CPU scene reproduces the same trajectory. A unit test pins the per-device scene attributes.
Replace the per-test Nucleus-robot scenes with one module-scoped scene per device built from locally authored islands of the branching fixture. Each island serves one test, is reset once, and uses two environments where a partial write must prove the other environment keeps its backend state. The CUDA scene keeps the pinned-host staging, native Newton actuator, dynamics, tendon, floating-root, and FK-refresh tests. The CPU scene covers the host-resident property path and the host actuator path, so the file no longer needs one process per device. Unit-level articulation data and actuator-control tests move verbatim to unit modules.
Rigid-object and collection tests share one module-scoped scene of locally authored cuboids per device instead of rebuilding Nucleus props per test. They keep the partial-state, raw inertial, fused-layout, material, wrench, kinematic, and scene-data-provider checks, and the reset checks that make both wrench composers active first. A strict xfail pins a collection bug: a partial body pose write pushes whole environment rows from a pose buffer that is not refreshed first, so the unselected bodies of that environment are rewound to stale poses. The CPU deformable rejection test no longer needs a spawned child process.
Take over what the removed OVPhysX real-backend joint-state test checked, on every backend: unsorted int64 environment and joint selectors on the fused writer, the finite-difference baseline it restarts for the written joints, skip_forward leaving body caches to the caller, and the deprecated combined writer producing the same state as the public writers.
Run the PhysX articulation checks against one module-scoped scene built from the local branching fixture instead of per-test Nucleus robots. The scene holds two-environment islands (fixed with MJWarp ordering and USD gains, floating with configured gains, floating with a root-moving body order, and fixed with a reversed joint and a spatial tendon), so partial writes target environment 1 and prove environment 0 is preserved in the real PhysX state. Keep the Shadow Hand fixed-tendon, Franka gravity-compensation, and Franka IK tests on their shipped assets, and check initialization failures on the local fixture. Move the kernel unit tests under unit/ and cover the effort termination term with a core unit test.
…enes Share one module-scoped scene of locally authored cubes per file instead of a Nucleus scene per test. Partial state, inertial, and wrench writes select environment 1 or non-sorted body-major subsets and read the PhysX view back; center-of-mass offsets check every root and body frame writer and the spin kinematics. Failure modes, the gravity vector, physics warmup, and the collection subset regressions keep their own scenes. The rigid-object articulation-root rejection is kept as a strict xfail: the check was removed from the PhysX rigid object, and the previous Nucleus fixture only failed because it resolved no rigid body.
Drop the ideal-PD, DC-motor, and remotized-PD equivalence runs, whose actuator translation is backend independent: the mixed implicit/explicit run still exercises the PD and DC-motor authoring on PhysX, and the Newton suite owns the remaining models. Move the native-path preparation checks to a kitless unit file, and replace the graph-capture failure and outer-capture rollouts with unit tests of the shared PhysX actuator runtime.
Replace the disabled deformable suite with one scene of locally authored surface and volume meshes that need no mesher or collision cooking, and check partial nodal writes, kinematic targets, and the surface target rejection. Author the surface gripper locally, keep the CI skip for the real open/close seam, and check the command and property payloads with a recording view.
Bring the tracking branch to the union of the 24 series branches after aligning them with the coding and testing guidelines in docs/source/refs/contributing.rst.
Bring the tracking branch to the union of the series branches after the independent review round.
Consolidated to 13 PRsThe series is now 13 PRs instead of 24: #8134, #8135, #8138, #8139, #8141, #8144, #8146, #8147, #8149, #8151, #8153, #8154 and #8156, titled "Accelerate and strengthen asset tests [N/13]".
|
|
run-ci |
Description
The asset tests repeated expensive scenes, replayed the same contracts on every backend, and carried custom scaffolding that made them hard to follow. This PR consolidates them across PhysX, Newton, and OVPhysX into lean, directly readable tests: cheap mocked contracts own the shared API, and real-solver tests only cover what needs the real solver.
This is the combined PR for review and merge. The split PRs are not being updated.
Test organization
source/isaaclab/test/assets/contract/):test_articulation_contract.py(including joint/body ordering) andtest_rigid_object_contract.py(rigid objects and collections, one factory) run every backend on mocked views.backends.pyowns the Kit/kitless bootstrap, backend availability, and the manager doubles; unavailable backends collect as skips. Newton runs on CPU only, since its asset code has no CUDA-specific path; PhysX and OVPhysX keep CUDA rows for their pinned-staging paths.isaaclab_newton/test/assets/data) instead of ANYmal.What was removed or merged
capabilities.py,contract_boot.py,mock_backends.py,public_surface.py, and tests that only exercised test scaffolding or a copied member inventory._make_*variants; tests that rebuilt the same mocked asset to check overlapping properties.device_splitrunner support (tools/_device_split.py, its test, the pytest marker, and workflow mentions). No test declares it after the OVPhysX device fix below.DC_MOTOR_ACTUATORSandActuatorStateResetBasefromisaaclab.test.utils.actuator_equivalence, which no longer have callers.Every merged or removed contract has a keeper. Non-obvious merges were checked with a one-line production mutation that turns the keeper red (for example, writer kernels ignoring the mask, COM caches not invalidated, Jacobian link shift skipped, collection COM/inertia fixes reverted).
Coverage deliberately given up: the Lab-path DelayedPD reset check now runs on Newton only (PhysX asserts reset forwards environment IDs); armature-to-mass-matrix invalidation is no longer tested because PhysX does not reflect armature writes in the mass matrix within one step; PhysX composite-scene checks run on CUDA only (CPU staging stays covered by the mocked contracts); OVPhysX collision isolation, mimic fingers, and non-geometry heterogeneous articulation variants run on CUDA only.
Runtime changes included in this PR
Validation
Each file ran in its own process on an NVIDIA RTX PRO 6000 Blackwell (warm Warp cache), comparing the head of this PR before the cleanup (
ad9b10a37) with the current one:Current results: 1,042 passed, 31 skipped, 10 strict xfails, 99 deselected (Newton CUDA contract rows). The OVPhysX sensor, view, and randomization files are unchanged apart from dropping their device-split fixtures (~134 s, not counted above). Fewer files also means fewer Kit launches in CI, where each one costs more than locally.
Formatting, lint, LFS, and whitespace hooks pass. The changelog check passes against upstream
develop.Known failures pinned as strict xfails
Other limitations exposed by the redesign and left out of scope: full PhysX collection reset leaves wrench composers active; GPU link-frame wrench delivery can use stale transforms after teleports; Newton native-actuator reset is model-wide.
Type of change
device_splitremoval)Checklist
CONTRIBUTORS.md