T09 · Insecure Skill Coding Practices
- Location
scripts/generate_story_video.py:302- Finding
Shell Command Injection Through the User-Controlled Story Theme
- Content
View full analysis
- Remediation
View remediation
Security audit
Security checks for vulnerabilities and agentic risk
The skill is mostly a coherent ComfyUI story-video generator, but its script can turn a crafted story theme into arbitrary shell command execution.
Review or patch the script before installing. In particular, replace os.system with subprocess argument lists, treat the theme as untrusted input, use a virtual environment with pinned dependencies, and expect generated files to be written under output/.
scripts/generate_story_video.py:302Shell Command Injection Through the User-Controlled Story Theme
SKILL.md:20Unpinned Third-Party Python Dependencies
The TTS shell command embeds unsanitized story text into a shell string passed to os.system. Because theme input is user-controlled and flows into scene text, an attacker can inject shell syntax and achieve arbitrary command execution when the script generates narration.
This os.system call builds a shell command using the scene text directly inside double quotes. If the text contains shell metacharacters such as quotes, command substitution, or escapes, an attacker can break out of the intended argument and execute arbitrary commands on the host running the script.
# 使用 say 命令生成语音
cmd = f'say -v "Ting-Ting" -o "{temp_aiff}" "{text}"'
os.system(cmd)
# 转换为 mp3
cmd = f'ffmpeg -i "{temp_aiff}" -codec:a libmp3lame -qscale:a 2 "{output_path}" -y 2>/dev/null'
os.system() and os exec-family calls run shell commands with the process's full privileges, enabling arbitrary command execution.
# 转换为 mp3
cmd = f'ffmpeg -i "{temp_aiff}" -codec:a libmp3lame -qscale:a 2 "{output_path}" -y 2>/dev/null'
os.system(cmd)
# 删除临时文件
if os.path.exists(temp_aiff):
os.system() and os exec-family calls run shell commands with the process's full privileges, enabling arbitrary command execution.
# 简化版本:只合成图片序列
cmd = f'ffmpeg -f concat -safe 0 -i "{list_file}" -vf "fps=30,format=yuv420p" -c:v libx264 -pix_fmt yuv420p "{output_path}" -y 2>&1'
result = os.system(cmd)
# 清理临时文件
if list_file.exists():
The examples and customization guidance are explicitly centered on Chinese content, including Chinese theme values and Chinese voice selection. Because the documentation does not present this as optional or offer a language/locale choice, it can be read as imposing a specific language preference.
The README is entirely Chinese, examples use Chinese themes, and the TTS guidance instructs users to select Chinese voices, while only mentioning English for an optional third-party TTS later. This indicates a language/locale constraint without explicit user opt-in or a documented justification for limiting the skill to Chinese usage.
Natural-language strings throughout the skill are Chinese, and the TTS voice is hardcoded to a Chinese voice (Ting-Ting). This imposes a specific language/locale behavior without any opt-in or user-selectable language setting, which matches the policy concern for forced language selection.
The code saves generated images, audio, JSON metadata, temporary concat lists, and output media files, and also removes temporary files. Although some success messages are printed after certain writes, there is no upfront warning or clear disclosure in the skill description/docstring that running the script will create and clean up files under the output directory.
The create_video docstring says it will compose the final video, and comments at L327-L336 describe combining images, audio, and subtitles. However, the first command that references audio is overwritten at L337 by a simplified ffmpeg invocation that only uses the image concat list, so no narration audio is included in the output.
The module docstring and run docstring describe a complete pipeline from story generation to video output. In practice, run generates story text, images, audio, and saves JSON metadata, but it never invokes create_video, despite printing a video composition step at L393 and constructing video_path at L395.
This markdown file documents creation of multiple output artifacts under output/, including JSON, PNG, MP3, and MP4 files, but it does not include any user warning about modifying local files or consuming disk space. For markdown files, SQP-2 applies when descriptions omit warnings about behaviors that could affect user data or system state.
No suspicious patterns detected.