Skip to content

fix(image_processor): maintain 3-tuple return contract in InpaintProcessor.preprocess when mask is None - #14481

Open
patrickswedish wants to merge 1 commit into
huggingface:mainfrom
patrickswedish:fix-inpaint-processor-preprocess-contract
Open

patrickswedish wants to merge 1 commit into
huggingface:mainfrom
patrickswedish:fix-inpaint-processor-preprocess-contract

Conversation

@patrickswedish

Copy link
Copy Markdown

What does this PR do?

Fixes #14470.

InpaintProcessor.preprocess returns a 3-tuple (image, mask, postprocessing_kwargs) across all masked execution paths, but when mask is None, the early return returned only the processed image tensor directly. Callers unpacking the standard 3-value contract (image, mask, postprocessing_kwargs = processor.preprocess(...)) would raise ValueError: not enough values to unpack (expected 3, got 1).

Root Cause

When the 3-value contract and postprocessing_kwargs were introduced in commit f50b18eec (#12220), the early return for mask is None was not updated to return the consistent 3-tuple structure. Additionally, the return type annotation indicated tuple[torch.Tensor, torch.Tensor], which did not reflect the 3-element return value or optional mask.

Changes

  • Updated InpaintProcessor.preprocess in src/diffusers/image_processor.py when mask is None to return (processed_image, None, postprocessing_kwargs) where postprocessing_kwargs is populated with {"crops_coords": None, "original_image": None, "original_mask": None}.
  • Updated return type annotation to tuple[torch.Tensor, torch.Tensor | None, dict[str, Any]].
  • Added unit tests in tests/others/test_image_processor.py covering preprocess with mask, without mask (mask=None), and with padding_mask_crop.

Before submitting

Who can review?

@DN6 @yiyixuxu

@lindicaphxag-tech

Copy link
Copy Markdown

I closed my duplicate #14807 in favor of this PR after comparing the diffs. This change covers the same no-mask contract and also tests masked and padding-crop paths with the precise optional-mask return type. Could a maintainer review or identify any remaining concern?

Comment thread tests/others/test_image_processor.py Outdated
assert postprocessing_kwargs["original_image"] is None
assert postprocessing_kwargs["original_mask"] is None

def test_inpaint_processor_preprocess_with_padding_mask_crop(self):

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

can we just reduce to one test? you can use @pytest.mark.parametrize

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

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

Thanks for the feedback, @yiyixuxu! Updated to consolidate into a single @pytest.mark.parametrize test covering the with-mask, without-mask, and crop configurations. Rebased cleanly on latest main, squashed to a single atomic commit, and verified all tests and linting pass locally.

…one (huggingface#14470)

Ensure InpaintProcessor.preprocess returns (image, None, postprocessing_kwargs) when mask is None, preserving the expected 3-tuple return contract and signature consistency across all preprocess branches. Consolidate unit tests into a parameterized test covering with-mask, without-mask, and crop configurations.
@patrickswedish
patrickswedish force-pushed the fix-inpaint-processor-preprocess-contract branch from 8816fd2 to b9bb68a Compare October 3, 2026 13:16
@github-actions github-actions Bot added size/S PR with diff < 50 LOC fixes-issue and removed size/M PR with diff < 200 LOC labels Oct 3, 2026

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

fixes-issue size/S PR with diff < 50 LOC tests

Projects

None yet

Development

Successfully merging this pull request may close these issues.

InpaintProcessor.preprocess returns a bare tensor when no mask is passed, breaking its own 3-value contract

3 participants