keras-team/keras · error · ValueError

Invalid image2 rank: expected rank 3 (single image) or rank

Error message

Invalid image2 rank: expected rank 3 (single image) or rank 4 (batch of images). Received input with shape: image2.shape={image2.shape}

What it means

The SSIM op's shape validation for image2: it must be rank 3 or rank 4, mirroring the image1 check. It fires when the second (target/reference) image has the wrong rank.

Source

Thrown at keras/src/ops/image.py:2727

            image1,
            image2,
            max_val=self.max_val,
            filter_size=self.filter_size,
            filter_sigma=self.filter_sigma,
            k1=self.k1,
            k2=self.k2,
            data_format=self.data_format,
        )

    def compute_output_spec(self, image1, image2):
        if len(image1.shape) not in (3, 4):
            raise ValueError(
                "Invalid image1 rank: expected rank 3 (single image) "
                "or rank 4 (batch of images). Received input with shape: "
                f"image1.shape={image1.shape}"
            )
        if len(image2.shape) not in (3, 4):
            raise ValueError(
                "Invalid image2 rank: expected rank 3 (single image) "
                "or rank 4 (batch of images). Received input with shape: "
                f"image2.shape={image2.shape}"
            )
        # Output is a scalar per image in the batch
        if len(image1.shape) == 3:
            output_shape = ()
        else:
            output_shape = (image1.shape[0],)
        return KerasTensor(shape=output_shape, dtype=image1.dtype)


@keras_export("keras.ops.image.ssim")
def ssim(
    image1,
    image2,
    max_val=1.0,
    filter_size=11,

View on GitHub (pinned to 7a34a03db6)

Solutions

  1. Batch the reference: image2[None, ...] to match rank 4.
  2. Add a channel axis to grayscale ground truth.
  3. Verify image1.shape == image2.shape before calling ssim.

Example fix

# before
ssim(preds, ref_img, 1.0)  # preds (N,H,W,C), ref (H,W,C)

# after
ssim(preds, np.stack([ref_img] * len(preds)), 1.0)
Defensive patterns

Strategy: validation

Validate before calling

import numpy as np
a, b = np.asarray(image1), np.asarray(image2)
if b.ndim == a.ndim - 1: b = np.stack([b] * a.shape[0])
assert a.shape == b.shape, (a.shape, b.shape)

Type guard

def same_image_shapes(a, b):
    return np.asarray(a).shape == np.asarray(b).shape and np.asarray(a).ndim in (3, 4)

Prevention

When it happens

Trigger: ssim(image1 (N,H,W,C), image2 (H,W,C)) with unbatched ground truth; image2 stored as a rank-2 grayscale array.

Common situations: Comparing a model's batched predictions against a single reference image; dataset ground-truth stored channel-less.

Related errors


AI-assisted analysis of keras-team/keras@7a34a03db6 (2026-08-25). Data as JSON: /api/errors/0a9fd1b84f4fd691. Report an issue: GitHub.