Skip to content

fix(LoadImage): raise OptionalImportError when user-specified reader is not installed#8823

Open
KamayaniR wants to merge 3 commits intoProject-MONAI:devfrom
KamayaniR:fix/load-image-raise-when-reader-not-installed
Open

fix(LoadImage): raise OptionalImportError when user-specified reader is not installed#8823
KamayaniR wants to merge 3 commits intoProject-MONAI:devfrom
KamayaniR:fix/load-image-raise-when-reader-not-installed

Conversation

@KamayaniR
Copy link
Copy Markdown

What does this PR do?

Fixes #7437

When a user explicitly specifies a reader in LoadImage (e.g. LoadImage(reader="ITKReader")),
and the required package is not installed, the previous behavior was to silently warn and
continue with fallback readers. This masked real configuration errors.

Changes

  • monai/transforms/io/array.py: Changed warnings.warn to raise OptionalImportError
    in the user-specified reader path inside LoadImage.__init__
  • tests/transforms/test_load_image.py: Added TestLoadImageReaderNotInstalled to verify
    the exception is raised correctly

Behavior

Before:
LoadImage(reader="ITKReader") # itk not installed

UserWarning: silently falls back to another reader — user has no idea!

After:
LoadImage(reader="ITKReader") # itk not installed

OptionalImportError: required package for reader ITKReader is not installed

Checklist

  • Fixes the reported issue
  • Backward compatible (only affects explicit reader= usage)
  • Linting passes (ruff check)
  • Test added
  • Signed-off (git commit -s)

…package is not installed

Previously, if a user explicitly passed a reader name (e.g. reader="ITKReader")
and the required package was not installed, LoadImage would only emit a warning
and silently continue with fallback readers. This masked real configuration errors.

Now an OptionalImportError is raised immediately, making the failure explicit.
The auto-select path (reader=None) is unchanged and still skips missing readers silently.

Fixes Project-MONAI#7437

Signed-off-by: Kamayani Rai <kamayanirai78@gmail.com>
@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai bot commented Apr 12, 2026

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: c708f7be-1f9d-4561-aaba-cf9fd040f3ed

📥 Commits

Reviewing files that changed from the base of the PR and between 3194a78 and 78d9a93.

📒 Files selected for processing (1)
  • tests/data/test_init_reader.py
✅ Files skipped from review due to trivial changes (1)
  • tests/data/test_init_reader.py

📝 Walkthrough

Walkthrough

The change makes LoadImage.init re-raise an OptionalImportError (using raise ... from e) when a user-specified reader's import/initialization fails, instead of issuing a warning and falling back to another reader. The TypeError path that warns and falls back remains unchanged. Tests were added/updated: a new test asserts LoadImage(reader="ITKReader") propagates OptionalImportError when the reader init raises it, and tests that instantiate LoadImaged now catch and tolerate OptionalImportError for optional readers (with a special-case that reader=None must not raise).

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 50.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed Title clearly and concisely summarizes the main change: raising OptionalImportError when a user-specified reader is not installed.
Description check ✅ Passed Description covers the issue fix, changes made, behavior before/after, and includes a completed checklist matching the template structure.
Linked Issues check ✅ Passed PR directly addresses #7437: replaces silent warning with OptionalImportError for explicit reader specification, maintaining backward compatibility for auto-select (reader=None).
Out of Scope Changes check ✅ Passed All changes are in-scope: modified LoadImage.init error handling, added targeted test, and adapted test infrastructure to handle the new exception behavior.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ 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 and usage tips.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (2)
tests/transforms/test_load_image.py (2)

509-511: Tighten the exception assertion.

assertRaises(OptionalImportError) is broad. Prefer assertRaisesRegex(...) to verify the intended failure path/message.

Proposed test hardening
-        with self.assertRaises(OptionalImportError):
+        with self.assertRaisesRegex(OptionalImportError, "required package for reader ITKReader|itk not installed"):
             LoadImage(reader="ITKReader")
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/transforms/test_load_image.py` around lines 509 - 511, The test
currently catches any OptionalImportError broadly; tighten it by using
assertRaisesRegex to assert the specific error message from ITKReader's __init__
side-effect. Replace the nested assertRaises(OptionalImportError) around
LoadImage(reader="ITKReader") with self.assertRaisesRegex(OptionalImportError,
r"itk not installed") (or an appropriate regex matching the exact message
thrown) so the test verifies the intended failure path from ITKReader.__init__.

501-503: Add Google-style docstrings for new definitions.

Please add a class docstring and make the method docstring Google-style (including Raises), per repo guideline expectations.

As per coding guidelines, "Docstrings should be present for all definition which describe each variable, return value, and raised exception in the appropriate section of the Google-style of docstrings."

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/transforms/test_load_image.py` around lines 501 - 503, Add a
Google-style class docstring to TestLoadImageReaderNotInstalled describing the
test class purpose, and convert the
test_raises_when_user_specified_reader_not_installed docstring to a Google-style
docstring that includes Args (if any), a short description, and a Raises section
documenting that OptionalImportError is expected to be raised; update the
docstrings for the class TestLoadImageReaderNotInstalled and its method
test_raises_when_user_specified_reader_not_installed accordingly so they follow
the repository's Google-style docstring conventions.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@tests/transforms/test_load_image.py`:
- Around line 509-511: The test currently catches any OptionalImportError
broadly; tighten it by using assertRaisesRegex to assert the specific error
message from ITKReader's __init__ side-effect. Replace the nested
assertRaises(OptionalImportError) around LoadImage(reader="ITKReader") with
self.assertRaisesRegex(OptionalImportError, r"itk not installed") (or an
appropriate regex matching the exact message thrown) so the test verifies the
intended failure path from ITKReader.__init__.
- Around line 501-503: Add a Google-style class docstring to
TestLoadImageReaderNotInstalled describing the test class purpose, and convert
the test_raises_when_user_specified_reader_not_installed docstring to a
Google-style docstring that includes Args (if any), a short description, and a
Raises section documenting that OptionalImportError is expected to be raised;
update the docstrings for the class TestLoadImageReaderNotInstalled and its
method test_raises_when_user_specified_reader_not_installed accordingly so they
follow the repository's Google-style docstring conventions.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: ea3fe7f5-762b-476f-8de4-72874842db42

📥 Commits

Reviewing files that changed from the base of the PR and between 5a2d0a7 and b1ce780.

📒 Files selected for processing (2)
  • monai/transforms/io/array.py
  • tests/transforms/test_load_image.py

…eaders

- tests/data/test_init_reader.py: wrap LoadImaged init in try/except
  OptionalImportError since packages may not be installed in min-dep envs
- tests/transforms/test_load_image.py: tighten assertion using
  assertRaisesRegex, add Google-style class and method docstrings

Signed-off-by: Kamayani Rai <kamayanirai78@gmail.com>
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

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 the current code and only fix it if needed.

Inline comments:
In `@tests/data/test_init_reader.py`:
- Around line 30-34: The test currently silences OptionalImportError around the
LoadImaged instantiation, hiding real failures (e.g., reader=None); change the
handler so you do not silently swallow all errors: when creating
LoadImaged("image", reader=r) catch OptionalImportError as e and call
self.skipTest(f"missing optional dependency: {e}") or re-raise the exception for
any other unexpected condition (or assert r is not None before instantiation),
ensuring LoadImaged failures due to logic bugs are not hidden while still
skipping tests when a dependency truly isn't installed.
🪄 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: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 948aae05-0d26-4453-adab-fb0162baad6f

📥 Commits

Reviewing files that changed from the base of the PR and between b1ce780 and 3194a78.

📒 Files selected for processing (2)
  • tests/data/test_init_reader.py
  • tests/transforms/test_load_image.py
🚧 Files skipped from review as they are similar to previous changes (1)
  • tests/transforms/test_load_image.py

Use subTest per reader and explicitly fail if reader=None raises
OptionalImportError, preventing silent swallowing of real logic bugs.

Signed-off-by: Kamayani Rai <kamayanirai78@gmail.com>
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.

Raise the exception when LoadImage has a reader specified but it is not installed

1 participant