Repository navigation
PP-5: masks (stated axes, never converted, labels always used) - #111
Merged
Merged
Conversation
Plan-structure audit §5, to make room for the mask work. No behaviour change. - masks/model.py: MaskFile, MaskInventory and the constants. - masks/files.py: find_masks and the pairing. - masks/header.py: the header without pixels. - masks/layout.py: the stored axes and plane index. - masks/read.py: read_mask, read_mask_file. - masks/checks.py: header checks, mask_plane_issues. - masks/labels.py: check_labels, LARGEST_LABEL. morphobricks_preprocessing.masks re-exports the public names. The modules are layered so that there is no import cycle. Baseline entries are re-keyed with --rename. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WX6rdMV1r5jUPUR94kxV5a
- Plain-stack masks get their axes stated once per mask type (--mask-axes TYPE=ROLES, mask_axes=); a 2-D mask on a multi-plane image is shared only when stated YX. Recorded as axes_from "stated" and shared in the manifest. - A mask stored with Y and X the other way round from its image is the error mask_layout with a numpy.swapaxes hint; masks are never transposed. - image_named_as_mask becomes an error (rename or exclude); _masks and _cp_masks join the mask name suffixes. Excluding the file clears it. - Masks of excluded images are reported apart (mask_of_excluded_image); unpaired masks stay a warning, as every existing check keeps its severity. - output_inside_masks error. - OME-Zarr label images are always used (ome_zarr_labels removed) and are fingerprinted per label, outside the image's fingerprint. - Name helpers move from discovery.py to image_names.py and mask_names.py; axis-name constants to axis_names.py. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WX6rdMV1r5jUPUR94kxV5a
Conflicts resolved hunk by hunk: - run/pipeline.py: PP-5's mask_axes with main's unchanged_confirmation and asdict counts. - docs/contract.md: main's error row (axes_x_before_y) plus the errors PP-5 added but had not listed there (image_named_as_mask, output_inside_masks, mask_layout, invalid_mask_axes, mask_axes_contradict_header); PP-5's warning row. - tools/code_rules_baseline.json: the lower value of each entry, PP-5's renames, main's noqa counts; run_experiment 159 lines. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WX6rdMV1r5jUPUR94kxV5a
A stated plain-stack mask was recorded with axes and roles both "TYX", so
the manifest lost how the mask is stored ("IYX"): a brick reading it from
the manifest could not read it as stored. The manifest's mask "axes" are
now the header's letters, "roles" what they are read as.
Contract §9: the masks entry describes axes_from "stated" and shared true
(it still said header/false and "the manifest stays version 1"), and that
label images give a masks entry without a masks folder.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01WX6rdMV1r5jUPUR94kxV5a
guijacquemet
marked this pull request as ready for review
November 1, 2026 17:48
Contributor
Author
|
Independent review of PP-5 (design v0.4 rev 4 §2, §3, §6, §9, and the change log). Brought up to date: merged main after PP-4 (
Finding, fixed in Verified:
Generated by Claude Code |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
PP-5 of the v0.4.0 plan (design v0.4 §2, §3). Based on main: PP-4 (#110) is merged, and main was merged in (
fdf16fb).Commits
54a68d8moves code only:masks.pybecomes themasks/package (model, files, header, layout, read, checks, labels).88a14b8holds the feature work below.fdf16fbmerges main (PP-4 with its review fix).3b572cais a review fix: a mask's manifestaxesare its stored axes (IYX), beside itsroles(TYXwhen stated); the contract's masks entry now describesstatedandshared.Behaviour changes
--mask-axes TYPE=ROLESoncheck,runandmasks, ormask_axes=inpreflightandrun_experiment. The statement also covers masks of that type added later.invalid_mask_axes. So does a statement for a mask type that isn't found.mask_axes_contradict_header.axes_from: "stated".mask_planes_mismatch, unless its type is statedYX. Then one plane is shared by every plane of the image, recorded asshared: true, andread_maskreturns it for anyz/t.mask_layoutwith anumpy.swapaxeshint. Before, the second case wasmask_size_mismatch.image_named_as_maskis now an error. It was a warning. To clear it, rename the file or exclude it; an excluded file is no longer reported._masksand_cp_masksare added toMASK_NAME_SUFFIXES.mask_of_excluded_image, instead ofmask_without_image. Unpaired masks stay a warning, because §3 keeps the severity of every existing check (see the question below).output_inside_masks.labels/are always used. Theome_zarr_labelsparameter is removed frompreflight,run_experimentandfind_masks. Each label image has its own fingerprint. Thelabelsgroup is left out of the image'ssource_fingerprint, so adding a label image doesn't recompute the image's rows.position_id,IMAGE_SUFFIXESandNAME_SUFFIXESmove toimage_names.py.mask_names.py.axis_names.py.Tests
tests/test_masks_v040.pyhas 26 tests. On the PP-4 code, 23 of them fail. The other 3 pass there on purpose, because they guard behaviour that stays the same: a single-plane 2-D mask needs no statement, a named TYX mask works, and unpaired masks stay a warning.mask_of_excluded_imageinstead ofmask_without_image;mask_layoutfor a swapped mask;image_named_as_maskwarning test moved into the new file as an error test.Gate (at
3b572ca)ruff checkandruff format --checkpass, and so doestools/check.py --rules. The baseline only went down: entries were removed, lowered, or renamed for the moved code.Notes
discovery.pyis 610 lines, still over the 600 limit but below its baseline entry, which went down.Owner answer
mask_without_imagestays a warning (owner, 1 November 2026; design change log).https://claude.ai/code/session_01WX6rdMV1r5jUPUR94kxV5a
Generated by Claude Code