Skip to content

Fix multi-grid standalone slide embedding - #7

Merged
CraigMyles merged 2 commits into
mainfrom
agent/fix-slide-embedding
Jul 11, 2026
Merged

Fix multi-grid standalone slide embedding#7
CraigMyles merged 2 commits into
mainfrom
agent/fix-slide-embedding

Conversation

@CraigMyles

@CraigMyles CraigMyles commented Jul 11, 2026

Copy link
Copy Markdown
Owner

Summary

  • add explicit --grid support and deterministic grid inference for standalone slide
    encoding
  • pass the selected grid level0_patch to position-aware encoders such as TITAN and
    GigaPath
  • share feature selection, provenance, completeness validation, and Zarr writes between
    inline and standalone paths
  • make unchanged reruns idempotent, repair malformed or mismatched outputs, and preserve
    intentional --force replacement
  • reject patch-model overrides that violate a specific slide encoder contract
  • validate every requested slide-encoder name before slide discovery, worker creation,
    model loading, or encoding
  • correct TITAN examples to use CONCH v1.5 at 512 px

Why

The standalone command still assumed a single grid and called position-aware encoders
without patch_size_lv0. Its duplicated implementation had also drifted from the inline
path, while inline reruns without receipts could fail when slide/<model> already
existed.

Impact

This adds one backward-compatible CLI option, --grid. Single-grid stores continue to
work without it. Multi-grid stores infer a unique grid from the requested patch model
where possible and otherwise return an actionable error. There is no store schema
change.

Existing slide outputs are skipped only when their array shape, dtype, role, patch-model
provenance, dimension, mirrored header metadata, and values are valid. A stale or
malformed output is recomputed. Standalone encoding refreshes consolidated metadata once
after the encoder loop; inline encoding does so once when the sink closes.

Root cause

Inline and standalone slide encoding maintained separate feature-selection,
spatial-argument, provenance, and write logic. The standalone copy predated multi-grid
stores and the patch_size_lv0 encoder contract.

Verification

  • 241 passed, 48 skipped, 14 deselected with pytest -q -m "not slow"
  • ruff check .
  • git diff --check
  • CLI help smoke test for slide-embed --help
  • wheel and source distribution build via uv build
  • independent focused code and test reviews found no remaining blockers
  • real TITAN cluster run on a 40x iCAIRD slide: a conch_v1_5 @512 grid recorded
    level0_patch=1024; standalone slide-embed -s titan passed 1024 to the encoder and
    produced a finite (1, 768) float32 slide/titan vector
  • incompatible --patch-model uni was rejected in the real-weight workflow

Closes #2
Part of #6

@CraigMyles
CraigMyles marked this pull request as ready for review July 11, 2026 22:25
@CraigMyles
CraigMyles merged commit 95db1f2 into main Jul 11, 2026
5 checks passed
@CraigMyles
CraigMyles deleted the agent/fix-slide-embedding branch July 11, 2026 22:26
CraigMyles added a commit that referenced this pull request Jul 13, 2026
## Summary

- pass each registry `weights_revision` to Hugging Face loaders whose
API accepts a
  revision
- for CONCH, KRONOS, OpenCLIP, and MADELEINE, download the pinned
revision first and
  give the upstream factory a local path
- verify the recorded SHA-256 before those local checkpoints reach an
upstream
  deserializer
- pin BiomedCLIP's nested PubMedBERT configuration to an immutable
revision and make
  both model construction and tokenizer configuration resolve locally
- pin every mutable `git+https` installation example to the audited
upstream commit
- require OpenCLIP 3.x for its supported `local-dir:` loading contract

## Why

The registry already records immutable model revisions, but several
loaders and install
examples did not enforce them. A store could therefore record one
revision while an
upstream factory or a copied install command resolved the repository's
current default
branch.

BiomedCLIP also contains a transitive dependency: its pinned top-level
`open_clip_config.json` names a separate mutable PubMedBERT repository.
OpenCLIP builds
that text tower even though raw2features exposes only `encode_image`, so
the nested
configuration must be pinned as well.

## Implementation

- `ClipHFEmbedder` forwards `revision=` to `AutoModel.from_pretrained`.
- CONCH and KRONOS download their exact checkpoint files at the registry
revision,
verify their registry digest, and pass only the verified local path
upstream.
- QuiltNet and BiomedCLIP use a raw2features-owned,
model-and-revision-specific cache
containing only `open_clip_config.json` and
`open_clip_pytorch_model.bin`; the exact
  `.bin` is verified before OpenCLIP loads `local-dir:<path>`.
- BiomedCLIP downloads `config.json`, `tokenizer_config.json`, and
`vocab.txt` from
  `microsoft/BiomedNLP-BiomedBERT-base-uncased-abstract` at
`d673b8835373c6fa116d6d8006b33d48734e305d`, then atomically rewrites the
app-owned
OpenCLIP config so both nested names are absolute local paths. The
shared Hugging Face
  cache is never modified.
- MADELEINE preserves `RAW2FEATURES_MADELEINE_DIR` and the existing
default cache
behavior, but downloads `model_config.json` and `model.pt` at the
recorded revision,
verifies `model.pt`, and calls the upstream local-path factory on the
requested
  device.
- VCS install instructions now pin CONCH, KRONOS, MUSK, MADELEINE, and
Prov-GigaPath;
the already-pinned SEAL example now also pins its CONCH backbone
example.

## Compatibility

There is no CLI or embeddings-store schema change. Model outputs,
preprocessing, and
recorded provenance fields are unchanged; the existing pins are now
enforced during
download and installation. OpenCLIP users need `open_clip_torch>=3.0`,
which provides
the local-directory loader used here.

## Validation

- `333 passed, 50 deselected` in the full non-slow suite after rebasing
onto merged
  PR #7, on Linux/Python 3.12 with the optional dependencies installed
- `22 passed` in the focused hub and loader-pinning tests
- `ruff check .`
- `git diff --check`
- independent review specifically checked the upstream loader contracts,
pinned VCS
revisions, transitive BiomedCLIP dependency, local-cache isolation, and
deserialize-before-verification boundary; its blocking findings were
fixed before
  the final test run
- no gated real-weight/GPU run was performed for this branch; loader
contracts are
  covered with isolated tests and upstream-source review

Closes #5
Part of #6
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Fix standalone slide embedding and multi-grid support

1 participant