diff --git a/llm/cli.py b/llm/cli.py index 8b6d56c..07cc35a 100644 --- a/llm/cli.py +++ b/llm/cli.py @@ -646,15 +646,17 @@ def prompt( # Need to validate and convert their types first model = get_model(model_id or get_default_model()) try: - to_save["options"] = dict( - (key, value) - for key, value in model.Options(**dict(options)) - if value is not None - ) + options_model = model.Options(**dict(options)) + # Use model_dump(mode="json") so Enums become their .value strings + to_save["options"] = { + k: v + for k, v in options_model.model_dump(mode="json").items() + if v is not None + } except pydantic.ValidationError as ex: raise click.ClickException(render_errors(ex.errors())) path.write_text( - yaml.dump( + yaml.safe_dump( to_save, indent=4, default_flow_style=False, diff --git a/tests/test_templates.py b/tests/test_templates.py index 55d3e55..dcdabd9 100644 --- a/tests/test_templates.py +++ b/tests/test_templates.py @@ -140,6 +140,15 @@ def test_templates_list(templates_path, args): }, None, ), + # Model option using an enum: https://github.com/simonw/llm/issues/1237 + ( + ["-m", "gpt-5", "-o", "reasoning_effort", "minimal"], + { + "model": "gpt-5", + "options": {"reasoning_effort": "minimal"}, + }, + None, + ), ), ) def test_templates_prompt_save(templates_path, args, expected, expected_error):