Make the array-api-strict suite green and promote the strict CI job - #1005
Conversation
flat_correct checked for masked flat pixels with the mask.any() method, which arrays of spec-only array-API namespaces (array-api-strict) do not have; use xp.any instead. Verified on numpy, dask, jax and array-api-strict. The two remaining strict failures are astropy-upstream and get accurate backend_xfail marks in line with the rest of the suite: - test_unit_mismatch_behaves_as_expected: astropy's arithmetic mixin builds the Quantity with `data << unit`, and array-api-strict rejects the astropy unit operand (see astropy#936). - test_rebin_ccddata[True-True]: astropy's CCDData.mask setter coerces the mask with np.asarray, which fails for an array on the non-default device. The stale xfail on test_flat_correct_masked_flat_with_immutable_array (its reason described an older failure mode) is removed; the test passes on every backend with the fix. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01LVxnTLrWKStBdPwcmDNhxA
The array-api-strict suite is green (839 passed, 46 xfailed locally), so retire the expected-failures carve-out: move py313-strict into the ci-tests matrix, where a test failure fails CI, and remove the continue-on-error step, the outcome artifact plumbing, and the strict_status.yml reporting workflow that existed only to surface the carve-out's real outcome on PRs. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01LVxnTLrWKStBdPwcmDNhxA
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## main #1005 +/- ##
=======================================
Coverage 97.96% 97.96%
=======================================
Files 9 9
Lines 1912 1912
=======================================
Hits 1873 1873
Misses 39 39
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Harness. 🚀 New features to boost your workflow:
|
There was a problem hiding this comment.
Pull request overview
Fixes the remaining project-owned array-API-strict failure and promotes the strict backend to required CI.
Changes:
- Uses
xp.anyfor backend-compatible mask checks. - Marks two Astropy limitations as expected strict-backend failures.
- Moves strict testing into the main CI matrix and removes legacy reporting.
Reviewed changes
Copilot reviewed 6 out of 6 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
CHANGES.rst |
Documents strict compatibility and CI promotion. |
ccdproc/core.py |
Makes flat-mask detection array-API compatible. |
ccdproc/tests/test_ccdproc.py |
Updates strict-backend expected failures. |
ccdproc/tests/test_rebin.py |
Marks an Astropy mask-setter incompatibility. |
.github/workflows/ci_tests.yml |
Makes strict test failures fail CI. |
.github/workflows/strict_status.yml |
Removes obsolete status reporting. |
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
| @pytest.mark.backend_xfail( | ||
| "array-api-strict", | ||
| reason="astropy's CCDData.mask setter coerces the mask with " | ||
| "np.asarray, which fails for an array-api-strict array on the " | ||
| "non-default device", | ||
| ) | ||
| @pytest.mark.parametrize("mask_data, uncertainty", [(False, False), (True, True)]) |
There was a problem hiding this comment.
Confirmed — backend_xfail is applied non-strict (conftest.py adds pytest.mark.xfail(reason=..., strict=False)), so with the function-level marker a genuine regression in the currently passing [False-False] case would be reported as an expected failure rather than failing the job. Will scope the marker to the failing case via the suite's existing per-parameter pattern (as with _GAIN_APPLY_STRICT_XFAIL in test_cosmicray.py):
@pytest.mark.parametrize(
"mask_data, uncertainty",
[
(False, False),
pytest.param(
True,
True,
marks=pytest.mark.backend_xfail(
"array-api-strict",
reason="astropy's CCDData.mask setter coerces the mask with "
"np.asarray, which fails for an array-api-strict array on "
"the non-default device",
),
),
],
)
def test_rebin_ccddata(mask_data, uncertainty):— Written by Claude at @mwcraig's direction.
| Other Changes and Additions | ||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||
|
|
||
| - The ``py313-strict`` CI job (the ``array-api-strict`` suite on a |
There was a problem hiding this comment.
Proposed shorter entry:
- The ``py313-strict`` CI job is now part of the regular CI matrix and fails
CI on a test failure; the expected-failures carve-out and the
``strict_status.yml`` reporting workflow are retired. [#1005]— Written by Claude at @mwcraig's direction.
| Bug Fixes | ||
| ^^^^^^^^^ | ||
|
|
||
| - ``flat_correct`` now checks whether the flat has any masked pixels with |
There was a problem hiding this comment.
Proposed shorter entry:
- ``flat_correct`` now checks the flat's mask with ``xp.any`` instead of the
``mask.any()`` method, which spec-only array-API namespaces do not
provide. [#1005]— Written by Claude at @mwcraig's direction.
…log entries Move the backend_xfail on test_rebin_ccddata into pytest.param marks for the (True, True) case only, so a regression in the passing (False, False) case is not swallowed by the non-strict xfail (Copilot's catch). Shorten the two changelog entries as requested. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01LVxnTLrWKStBdPwcmDNhxA
The 'Reading the strict CI signal' section in docs/array_api.rst still described the continue-on-error carve-out and the strict_status.yml check run, both removed by this PR; describe the promoted regular matrix job instead. Found by an adversarial review of the PR. Also make the changelog wording precise: it is the arrays of spec-only namespaces that lack the .any() method, not the namespaces. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01LVxnTLrWKStBdPwcmDNhxA
Follow-up to #1000/#1001, finishing the strict-backend items on the array-API migration list.
Commit 1 — make the strict suite green. The one remaining strict failure in ccdproc's own code was
flat_correctchecking the flat's mask with themask.any()method, which spec-only namespaces like array-api-strict don't provide; it now usesxp.any. The stalebackend_xfailontest_flat_correct_masked_flat_with_immutable_array(its reason described an older failure mode) is removed and the test passes everywhere. The two other strict failures are astropy-upstream and get accuratebackend_xfailmarks in line with the rest of the suite:test_unit_mismatch_behaves_as_expected: astropy's arithmetic mixin builds the Quantity withdata << unit, and array-api-strict rejects the astropy unit operand (see Array API: units/Quantity handling with non-numpy arrays #936).test_rebin_ccddata[True-True]: astropy'sCCDData.masksetter coerces the mask withnp.asarray, which fails for an array on the non-default device.Commit 2 — promote the strict CI job. With the suite green (839 passed, 46 xfailed, 0 failed locally), the expected-failures carve-out is retired:
py313-strictmoves into the regularci-testsmatrix where a failure fails CI, and thecontinue-on-errorstep, outcome-artifact plumbing, and thestrict_status.ymlreporting workflow are removed.Verified locally on the full suite for every backend: numpy (890 passed), dask (879 passed, escape-baseline ratchet enforced), jax (885 passed, ratchet enforced), array-api-strict (839 passed, 46 xfailed).
— Written by Claude at @mwcraig's direction.
🤖 Generated with Claude Code
https://claude.ai/code/session_01LVxnTLrWKStBdPwcmDNhxA