[cherry-pick release/v0.18.0post1][Bugfix] Enforce --max-generated-image-size on /v1/images/generations… (#2625)

Signed-off-by: David Chen <530634352@qq.com>
This commit is contained in:
WeiQing Chen authored and GitHub committed 2026-04-09 14:42:23 +08:00
1 parent 73d31edf63
commit 589e664947
2 files changed
+49 -21

No files matched your search

@@ -172,7 +172,7 @@ def test_client(mock_async_diffusion):
app.state.diffusion_model_name = "Qwen/Qwen-Image" # For models endpoint
app.state.args = Namespace(
default_sampling_params='{"0": {"num_inference_steps":4, "guidance_scale":7.5}}',
max_generated_image_size=4096, # 64*64
max_generated_image_size=1024 * 1792,
)
return TestClient(app)
@@ -239,7 +239,7 @@ def async_omni_stage_configs_only_client():
# AsyncOmni exposes stage_configs on the engine instance.
app.state.args = Namespace(
default_sampling_params='{"1": {"num_inference_steps":4, "guidance_scale":7.5}}',
max_generated_image_size=4096, # 64*64
max_generated_image_size=1024 * 1792,
)
return TestClient(app)
@@ -386,6 +386,18 @@ def test_image_edits_async_omni_stage_configs_only(async_omni_stage_configs_only
assert len(captured) == 2
def test_generate_images_max_size_rejected(async_omni_test_client):
"""Test that a size exceeding max_generated_image_size returns 400."""
response = async_omni_test_client.post(
"/v1/images/generations",
json={
"prompt": "a cat",
"size": "2048x2048", # 4,194,304 pixels > max_generated_image_size (1,048,576)
},
)
assert response.status_code == 400
def test_generate_multiple_images(test_client):
"""Test generating multiple images"""
response = test_client.post(
@@ -976,12 +988,13 @@ def test_image_edit_parameter_default_single_stage(test_client):
assert captured_sampling_params.num_inference_steps == 4
assert captured_sampling_params.guidance_scale == 7.5
# Size exceeding max_generated_image_size (1024*1792) returns 400
response = test_client.post(
"/v1/images/edits",
files=[("image", img_bytes_1)],
data={
"prompt": "hello world.",
"size": "96x96",
"size": "2048x2048",
},
)
assert response.status_code == 400
+33 -18
View File
@@ -1299,6 +1299,10 @@ async def generate_images(request: ImageGenerationRequest, raw_request: Request)
size_str = f"{width}x{height}"
else:
size_str = "model default"
app_state_args = getattr(raw_request.app.state, "args", None)
_check_max_generated_image_size(app_state_args, width, height)
_update_if_not_none(gen_params, "width", width)
_update_if_not_none(gen_params, "height", height)
@@ -1484,7 +1488,6 @@ async def edit_images(
)
# 3.3 Parse and add size if provided
max_generated_image_size = getattr(app_state_args, "max_generated_image_size", None)
width, height = None, None
if size.lower() == "auto":
if resolution is None:
@@ -1494,23 +1497,7 @@ async def edit_images(
else:
width, height = parse_size(size)
# Check max_generated_image_size
if max_generated_image_size is not None:
if width is not None and height is not None:
if width * height > max_generated_image_size:
raise HTTPException(
status_code=HTTPStatus.BAD_REQUEST.value,
detail=f"Requested image size {width}x{height} exceeds the maximum allowed "
f"size of {max_generated_image_size} pixels.",
)
elif resolution is not None:
# When resolution is set, the output size is resolution * resolution
if resolution * resolution > max_generated_image_size:
raise HTTPException(
status_code=HTTPStatus.BAD_REQUEST.value,
detail=f"Requested resolution {resolution} (max {resolution}x{resolution} pixels) "
f"exceeds the maximum allowed size of {max_generated_image_size} pixels.",
)
_check_max_generated_image_size(app_state_args, width, height, resolution)
size_str = f"{width}x{height}" if width is not None and height is not None else "auto"
_update_if_not_none(gen_params, "width", width)
@@ -1709,6 +1696,34 @@ async def _generate_with_async_omni(
return result
def _check_max_generated_image_size(
app_state_args: Any,
width: int | None,
height: int | None,
resolution: int | None = None,
) -> None:
"""Raise 400 if the requested image size exceeds --max-generated-image-size."""
max_generated_image_size = getattr(app_state_args, "max_generated_image_size", None)
# Check max_generated_image_size
if max_generated_image_size is None:
return
if width is not None and height is not None:
if width * height > max_generated_image_size:
raise HTTPException(
status_code=HTTPStatus.BAD_REQUEST.value,
detail=f"Requested image size {width}x{height} exceeds the maximum allowed "
f"size of {max_generated_image_size} pixels.",
)
elif resolution is not None:
# When resolution is set, the output size is resolution * resolution
if resolution * resolution > max_generated_image_size:
raise HTTPException(
status_code=HTTPStatus.BAD_REQUEST.value,
detail=f"Requested resolution {resolution} (max {resolution}x{resolution} pixels) "
f"exceeds the maximum allowed size of {max_generated_image_size} pixels.",
)
def _update_if_not_none(object: Any, key: str, val: Any) -> None:
if val is not None:
setattr(object, key, val)