harry0703/MoneyPrinterTurbo · error · BgmUploadError
background music file is empty or missing
Error message
background music file is empty or missing
What it means
Raised by validate_audio_file in app/services/bgm.py as a pre-check before invoking FFmpeg: the path either is not a regular file or has size <= 0 on disk. This guards the reusable validation entry point (used for both upload preflight with a 30s timeout and validating Sonilo-generated tracks up to 6 minutes with a 120s timeout) so FFmpeg is never invoked on missing/empty artifacts.
Source
Thrown at app/services/bgm.py:165
check=False,
)
except subprocess.TimeoutExpired as exc:
raise BgmServiceError("FFmpeg background music validation timed out") from exc
except OSError as exc:
raise BgmServiceError("failed to run FFmpeg for background music validation") from exc
if decoded.returncode != 0:
raise BgmUploadError("uploaded file must contain a decodable audio stream")
def validate_audio_file(file_path: str, timeout_seconds: int = 120) -> None:
"""
校验磁盘上的音频文件可由项目 FFmpeg 完整解码。
上传预检通常只需 30 秒;Sonilo 生成的配乐最长可达 6 分钟,因此对外提供
可调整超时的复用入口。服务只依赖 FFmpeg,不要求系统额外安装 FFprobe。
"""
if not os.path.isfile(file_path) or os.path.getsize(file_path) <= 0:
raise BgmUploadError("background music file is empty or missing")
_validate_audio(file_path, timeout_seconds=timeout_seconds)
def _stage_bgm_upload(filename: str, source: BinaryIO) -> tuple[str, str, int]:
"""
将上传流写入同目录临时文件,并返回安全文件名、临时路径和字节数。
WebUI 的上传预检和最终持久化必须使用完全相同的分块读取、大小限制与文件名
规则,否则可能出现界面显示可用、点击生成后却被服务端拒绝的状态分裂。
临时文件由调用方在完成音频探测后删除或原子替换。
"""
safe_name = sanitize_upload_filename(filename)
try:
target_dir = uploaded_bgm_dir(create=True)
except OSError as exc:
raise BgmServiceError("failed to prepare background music storage") from exc
temp_path = ""
total_bytes = 0View on GitHub (pinned to 1f9f19c202)
Solutions
- Confirm the file exists and has bytes before calling validation: os.path.isfile(p) and os.path.getsize(p) > 0.
- If a generated track is empty, the upstream generation step failed — re-run it rather than retrying validation.
- Use absolute paths resolved from a single tasks/storage root to avoid working-directory races.
Example fix
# before
validate_audio_file(possibly_missing_path)
# after
import os
if not os.path.isfile(possibly_missing_path) or os.path.getsize(possibly_missing_path) <= 0:
raise RuntimeError(f"audio artifact missing or empty: {possibly_missing_path!r}")
validate_audio_file(possibly_missing_path) Defensive patterns
Strategy: validation
Validate before calling
import os
def artifact_ready(path: str) -> bool:
return os.path.isfile(path) and os.path.getsize(path) > 0 Prevention
- Validate existence and non-zero size immediately before FFmpeg work.
- Propagate generation failures instead of letting empty files reach validation.
- Resolve artifact paths from a single absolute storage root.
When it happens
Trigger: Calling validate_audio_file on a path where the file was deleted or moved between staging and validation; a generated BGM file that was created but never written (0 bytes) due to a failed upstream step; a directory path passed instead of a file.
Common situations: Race between generation completion and validation in async pipelines; disk-full producing empty outputs; path typos or wrong working directory making os.path.isfile false.
Related errors
- background music must be a supported audio file inside stora
- {request_id}: {str(exc)}
- uploaded file must contain a decodable audio stream
- background music file exceeds the 30 MB limit
- background music file is empty
AI-assisted analysis of harry0703/MoneyPrinterTurbo@1f9f19c202 (2026-08-14).
Data as JSON: /api/errors/225cb015b5ec5665.
Report an issue: GitHub.