Skip to content

[Bugfix] Fix base64 JPEG video frames returning empty metadata#37301

Merged
Isotr0py merged 4 commits intovllm-project:mainfrom
he-yufeng:fix/video-base64-metadata
Mar 18, 2026
Merged

[Bugfix] Fix base64 JPEG video frames returning empty metadata#37301
Isotr0py merged 4 commits intovllm-project:mainfrom
he-yufeng:fix/video-base64-metadata

Conversation

@he-yufeng
Copy link
Copy Markdown
Contributor

Problem

Sending base64-encoded JPEG frames as video input returns a 400 error:

VideoMetadata.__init__() missing 1 required positional argument: 'total_num_frames'

VideoMediaIO.load_base64 handles the video/jpeg media type by decoding individual JPEG frames and stacking them, but returns an empty metadata dict {}. Downstream code passes this to transformers.video_utils.VideoMetadata(**metadata) which requires total_num_frames as a positional argument.

Root Cause

In vllm/multimodal/media/video.py:83-85:

return np.stack(
    [np.asarray(load_frame(frame_data)) for frame_data in data.split(",")]
), {}  # <-- empty metadata

All other video loading paths (via load_bytesvideo_loader.load_bytes) return properly populated metadata through create_hf_metadata(), but the base64 JPEG path was missed.

Fix

Populate the metadata dict with the same fields other loaders return:

  • total_num_frames: frame count from the stacked array
  • fps: from request kwargs (default 1)
  • duration: computed from total_num_frames / fps
  • video_backend: "jpeg_sequence" to distinguish from other backends
  • frames_indices: [0, 1, ..., N-1] since all frames are used directly
  • do_sample_frames: False since frames are pre-extracted by the client

Test plan

  • Verify base64 JPEG frame video input no longer returns 400
  • Ensure metadata fields match what VideoMetadata expects

Fixes #37274

When passing base64-encoded JPEG frames via `video/jpeg` media type,
`VideoMediaIO.load_base64` returned an empty metadata dict. Downstream
code tries to construct `VideoMetadata(**metadata)` which fails with:

  VideoMetadata.__init__() missing 1 required positional argument:
  'total_num_frames'

Populate the metadata dict with total_num_frames, fps, duration,
video_backend, and frames_indices — same fields that other video
loaders return via create_hf_metadata().

Fixes vllm-project#37274

Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Copy link
Copy Markdown
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

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

Code Review

The pull request effectively addresses the bug where base64-encoded JPEG video frames were returning empty metadata, leading to a VideoMetadata initialization error. The fix correctly populates the metadata dictionary with essential fields such as total_num_frames, fps, duration, video_backend, frames_indices, and do_sample_frames, ensuring compatibility with downstream video processing components. This is a critical improvement for the robustness of video input handling.

Comment on lines +90 to +98
metadata = {
"total_num_frames": total,
"fps": fps,
"duration": duration,
"video_backend": "jpeg_sequence",
"frames_indices": list(range(total)),
"do_sample_frames": False,
}
return frames, metadata
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

critical

The previous implementation returned an empty dictionary for metadata, which caused a runtime error when transformers.video_utils.VideoMetadata was initialized. This change correctly populates the metadata with all necessary fields, resolving the total_num_frames missing argument issue and ensuring proper video metadata propagation. This is a critical fix for the functionality of base64 JPEG video frame processing.

@mergify mergify bot added multi-modality Related to multi-modality (#4194) bug Something isn't working labels Mar 17, 2026
@mergify
Copy link
Copy Markdown

mergify bot commented Mar 17, 2026

Hi @universeplayer, the pre-commit checks have failed. Please run:

uv pip install pre-commit>=4.5.1
pre-commit install
pre-commit run --all-files

Then, commit the changes and push to your branch.

For future commits, pre-commit will run automatically on changed files before each commit.

Tip

Is mypy failing?
mypy is run differently in CI. If the failure is related to this check, please use the following command to run it locally:
# For mypy (substitute "3.10" with the failing version if needed)
pre-commit run --hook-stage manual mypy-3.10

@DarkLight1337 DarkLight1337 requested a review from Isotr0py March 17, 2026 15:13
Comment on lines -83 to -85
return np.stack(
[np.asarray(load_frame(frame_data)) for frame_data in data.split(",")]
), {}
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Can you add a regression test at tests/multimodal/media/test_video.py?

Signed-off-by: Yufeng He <40085740+he-yufeng@users.noreply.github.com>
Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
@mergify
Copy link
Copy Markdown

mergify bot commented Mar 18, 2026

Hi @universeplayer, the pre-commit checks have failed. Please run:

uv pip install pre-commit>=4.5.1
pre-commit install
pre-commit run --all-files

Then, commit the changes and push to your branch.

For future commits, pre-commit will run automatically on changed files before each commit.

Tip

Is mypy failing?
mypy is run differently in CI. If the failure is related to this check, please use the following command to run it locally:
# For mypy (substitute "3.10" with the failing version if needed)
pre-commit run --hook-stage manual mypy-3.10

Signed-off-by: Isotr0py <mozf@mail2.sysu.edu.cn>
@Isotr0py Isotr0py enabled auto-merge (squash) March 18, 2026 11:44
@github-actions github-actions bot added the ready ONLY add when PR is ready to merge/full CI is needed label Mar 18, 2026
@Isotr0py Isotr0py merged commit 918b789 into vllm-project:main Mar 18, 2026
47 checks passed
fxdawnn pushed a commit to fxdawnn/vllm that referenced this pull request Mar 19, 2026
…project#37301)

Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Signed-off-by: Yufeng He <40085740+he-yufeng@users.noreply.github.com>
Signed-off-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Co-authored-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Co-authored-by: Isotr0py <mozf@mail2.sysu.edu.cn>
SouthWest7 pushed a commit to SouthWest7/vllm that referenced this pull request Mar 27, 2026
…project#37301)

Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Signed-off-by: Yufeng He <40085740+he-yufeng@users.noreply.github.com>
Signed-off-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Co-authored-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Co-authored-by: Isotr0py <mozf@mail2.sysu.edu.cn>
khairulkabir1661 pushed a commit to khairulkabir1661/vllm that referenced this pull request Mar 27, 2026
…project#37301)

Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Signed-off-by: Yufeng He <40085740+he-yufeng@users.noreply.github.com>
Signed-off-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Co-authored-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Co-authored-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Monishver11 pushed a commit to Monishver11/vllm that referenced this pull request Mar 27, 2026
…project#37301)

Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Signed-off-by: Yufeng He <40085740+he-yufeng@users.noreply.github.com>
Signed-off-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Co-authored-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Co-authored-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Signed-off-by: Monishver Chandrasekaran <monishverchandrasekaran@gmail.com>
JiantaoXu pushed a commit to JiantaoXu/vllm that referenced this pull request Mar 28, 2026
…project#37301)

Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Signed-off-by: Yufeng He <40085740+he-yufeng@users.noreply.github.com>
Signed-off-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Co-authored-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Co-authored-by: Isotr0py <mozf@mail2.sysu.edu.cn>
vrdn-23 pushed a commit to vrdn-23/vllm that referenced this pull request Mar 30, 2026
…project#37301)

Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Signed-off-by: Yufeng He <40085740+he-yufeng@users.noreply.github.com>
Signed-off-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Co-authored-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Co-authored-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Signed-off-by: Vinay Damodaran <vrdn@hey.com>
EricccYang pushed a commit to EricccYang/vllm that referenced this pull request Apr 1, 2026
…project#37301)

Signed-off-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Signed-off-by: Yufeng He <40085740+he-yufeng@users.noreply.github.com>
Signed-off-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Co-authored-by: Yufeng He <40085740+universeplayer@users.noreply.github.com>
Co-authored-by: Isotr0py <mozf@mail2.sysu.edu.cn>
Signed-off-by: EricccYang <yangyang4991@gmail.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working multi-modality Related to multi-modality (#4194) ready ONLY add when PR is ready to merge/full CI is needed

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug]: vLLM serving cannot support video inputs with a list of base64-encoded extracted JPEG frames

2 participants