nexu-io/open-design · error · ValueError
--ppt-master-python must be Python 3.10 or newer
Error message
--ppt-master-python must be Python 3.10 or newer: {requested} What it means
Raised in humanize_ppt_v2.py when resolving `--ppt-master-python`. The resolver probes candidate Python interpreters by running a subprocess that prints its version and exits 0 only if `sys.version_info >= (3, 10)`. If the user explicitly requested an interpreter (the `requested` variable is set) and none of the probed candidates passed the version check, it raises ValueError. When no interpreter was explicitly requested, it silently falls back to ('python3', 'unverified').
Solutions
- Point --ppt-master-python at a Python 3.10+ interpreter: install one (pyenv install 3.11, brew install python@3.12, apt install python3.11) and pass its absolute path.
- Remove the --ppt-master-python flag to let the resolver auto-pick python3 (fallback path returns ('python3','unverified') instead of raising).
- Verify the candidate version directly: `/path/to/python -c "import sys; print(sys.version_info >= (3,10))"` — must print True.
- If using pyenv/conda, activate the environment first so `python3` resolves to 3.10+ before running humanize-ppt.
Example fix
// before python3 humanize_ppt_v2.py --ppt-master-python /usr/bin/python3 --source x.md # -> ValueError: --ppt-master-python must be Python 3.10 or newer: /usr/bin/python3 // after pyenv install 3.11 && pyenv global 3.11 # or: brew install python@3.12 python3 humanize_ppt_v2.py --ppt-master-python $(command -v python3) --source x.md
Defensive patterns
Strategy: validation
Validate before calling
import subprocess, sys
def python_at_least(path: str, minimum=(3, 10)) -> bool:
try:
r = subprocess.run(
[path, "-c",
f"import sys; raise SystemExit(0 if sys.version_info >= {minimum} else 1)"],
capture_output=True,
)
except OSError:
return False
return r.returncode == 0
if args.ppt_master_python and not python_at_least(args.ppt_master_python):
raise SystemExit(
f"--ppt-master-python must be Python 3.10+: {args.ppt_master_python}"
) Try / catch
try:
resolved, version = resolve_ppt_master_python(args.ppt_master_python)
except ValueError as exc:
raise SystemExit(str(exc)) from exc Prevention
- Standardize on Python 3.10+ across the project (set requires-python in pyproject).
- In CI matrices, drop 3.8/3.9 jobs or upgrade them.
- Let the resolver auto-pick by omitting --ppt-master-python when your default python3 is 3.10+.
- Document the minimum version prominently in the humanize-ppt README.
When it happens
Trigger: User passes `--ppt-master-python /usr/bin/python3.8` (or any 3.9-or-older interpreter); the candidate's version probe subprocess returns exit code 1; loop ends without a match; ValueError raised. Also fires if the requested path is valid but the version check subprocess errors out (returncode != 0) for every candidate.
Common situations: System default python3 is 3.8/3.9 (common on older Ubuntu/Debian LTS); user points at a conda/pyenv env built on an older Python; macOS where /usr/bin/python3 is older than the brew 3.x; CI matrix still pinned to 3.9.
Related errors
- BRAVE_API_KEY is required when web_backend='brave'
- brief mode reads markdown/text raw material, not rendered…
- EXA_API_KEY is required when web_backend='exa'
- last30days v3 requires Python 3.12+. Detected Python
- No sources are available for this run.
AI-assisted analysis of nexu-io/open-design@5be4028344 (2026-08-12).
Data as JSON: /api/errors/d6d6a94091930028.
Report an issue: GitHub.
Appendix: source
Thrown at plugins/community/humanize-ppt/scripts/humanize_ppt_v2.py:2654
continue
checked.add(resolved)
try:
result = subprocess.run(
[
resolved,
"-c",
"import sys; print('.'.join(map(str, sys.version_info[:3]))); raise SystemExit(0 if sys.version_info >= (3, 10) else 1)",
],
text=True,
capture_output=True,
)
except OSError:
continue
if result.returncode == 0:
return resolved, result.stdout.strip()
if requested:
raise ValueError(f"--ppt-master-python must be Python 3.10 or newer: {requested}")
return "python3", "unverified"
def write_ppt_master_source(out, title, plan, source, language):
"""Write a self-contained semantic source for PPT Master's Strategist.
PPT Master still owns design_spec/spec_lock and every native rendering
decision. This file freezes Humanize's page story, notes intent, and media
requirements so the downstream Strategist does not restart from raw source.
"""
source_path = Path(source).expanduser().resolve()
lines = [
"# Humanize PPT → PPT Master Source Contract",
"",
f"- Title: {title}",
f"- Language: {language}",
f"- Original source: `{source_path}`",
f"- Planned slides: {len(plan)}",View on GitHub (pinned to 5be4028344)