keras-team/keras · error · ValueError

Input images must have 3 channels, but received images with

Error message

Input images must have 3 channels, but received images with {channels} channels.

What it means

rgb_to_hsv requires exactly 3 channels on the channels axis (which it reads per data_format). Any other concrete channel count — most commonly 1 (grayscale) or 4 (RGBA) — raises this ValueError.

Source

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

    def compute_output_spec(self, images):
        images_shape = list(images.shape)
        dtype = images.dtype
        if len(images_shape) not in (3, 4):
            raise ValueError(
                "Invalid images rank: expected rank 3 (single image) "
                "or rank 4 (batch of images). "
                f"Received: images.shape={images_shape}"
            )
        if not backend.is_float_dtype(dtype):
            raise ValueError(
                "Invalid images dtype: expected float dtype. "
                f"Received: images.dtype={dtype}"
            )
        channels_axis = -1 if self.data_format == "channels_last" else -3
        channels = images_shape[channels_axis]
        if channels is not None and channels != 3:
            raise ValueError(
                "Input images must have 3 channels, but received images with "
                f"{channels} channels."
            )
        return KerasTensor(shape=images_shape, dtype=images.dtype)


@keras_export("keras.ops.image.rgb_to_hsv")
def rgb_to_hsv(images, data_format=None):
    """Convert RGB images to HSV.

    `images` must be of float dtype, and the output is only well defined if the
    values in `images` are in `[0, 1]`.

    All HSV values are in `[0, 1]`. A hue of `0` corresponds to pure red, `1/3`
    is pure green, and `2/3` is pure blue.

    Args:
        images: Input image or batch of images. Must be 3D or 4D.

View on GitHub (pinned to 7a34a03db6)

Solutions

  1. Convert grayscale to RGB by broadcasting the channel axis, and drop alpha: images = images[..., :3]
  2. Pass data_format='channels_first' when your tensors are (N,C,H,W)

Example fix

# before
hsv = keras.ops.image.rgb_to_hsv(gray)  # gray.shape=(H,W,1)

# after
rgb = keras.ops.broadcast_to(gray, gray.shape[:-1] + (3,))
hsv = keras.ops.image.rgb_to_hsv(rgb)
Defensive patterns

Strategy: validation

Validate before calling

c = images.shape[-1 if data_format == 'channels_last' else -3]
assert c is None or c == 3

Type guard

def is_rgb(images, data_format='channels_last') -> bool:
    return images.shape[-1 if data_format == 'channels_last' else -3] in (3, None)

Prevention

When it happens

Trigger: Passing grayscale (H,W,1) tensors or RGBA (H,W,4) tensors to rgb_to_hsv; passing channels_first data while leaving data_format at default so the wrong axis is read as channels.

Common situations: Applying HSV augmentation to a mixed dataset including grayscale images; alpha-channel PNGs; forgetting data_format='channels_first' for PyTorch-style tensors.

Related errors


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