flawopen.com/Command Injection/os.system()

Is os.system() always a command injection risk?

Reference page — draft, pending review
Short answer

It's risky whenever any part of the command string includes untrusted input — os.system() always runs its argument through a shell, with no way to opt out.

VULNERABLE
os.system(f"ping -c 1 {host}")
FIXED
subprocess.run(
  ["ping", "-c", "1", host]
)

Why os.system() is a structural problem, not just a misuse risk

Unlike subprocess.run(), which can be called without a shell, os.system() is defined to always pass its string to the platform's shell (/bin/sh on Unix). There's no argument-list form — any call to it that includes untrusted input needs the same shell-metacharacter awareness as shell=True, but without the option to remove the shell from the equation.

FAQ

Is there ever a safe use of os.system()?

Yes, when the entire command string is a fixed, hardcoded constant with no interpolated values at all. The moment any part of it is dynamic and traces back to outside input, it needs the subprocess module's list-argument form instead.

References