resolved RESOLVED PASS · 13 tool calls · 46 s · Textualize/rich
Fix raw markup printed on prompt errors sometimes ## Type of changes - [x] Bug fix - [ ] New feature - [ ] Documentation / docstrings - [ ] Tests - [ ] Other ## Checklist - [x] I've run the latest [black](https://github.com/psf/black) with default args on new code. - [ ] I've updated CHANGELOG.md and CONTRIBUTORS.md where appropriate (see note about typos above). - [x] I've added tests for new code. - [x] I accept that @willmcgugan may be pedantic in the code review. ## Description PromptBase.on_validate_error() should explicitly ask for markup in case the console passed to it has markup disabled globally. Fixes #3881.
| # | Tool | Arguments | Result |
|---|---|---|---|
| 1 | run_command | {
"command": "grep -rn \"PromptBase.on_validate_error\" ."
} | {"status": "error", "error_type": "CommandError", "error_message": "", "details": {"stdout": "", "stderr": "", "exit_code": 1}}full{"status": "error", "error_type": "CommandError", "error_message": "", "details": {"stdout": "", "stderr": "", "exit_code": 1}} |
| 2 | run_command | {
"command": "grep -rn \"on_validate_error\" ."
} | {"status": "ok", "stdout": "./rich/prompt.py:258: def on_validate_error(self, value: str, error: InvalidResponse) -> None:\n./rich/prompt.py:298: self.on_validafull{"status": "ok", "stdout": "./rich/prompt.py:258: def on_validate_error(self, value: str, error: InvalidResponse) -> None:\n./rich/prompt.py:298: self.on_validate_error(value, error)\n", "stderr": "", "exit_code": 0} |
| 3 | read_file | {
"filepath": "rich/prompt.py",
"start_line": "250",
"end_line": "270"
} | {"status": "error", "error_type": "FileReadError", "error_message": "'>' not supported between instances of 'int' and 'str'"}full{"status": "error", "error_type": "FileReadError", "error_message": "'>' not supported between instances of 'int' and 'str'"} |
| 4 | read_file | {
"end_line": "300",
"filepath": "rich/prompt.py",
"start_line": "250"
} | {"status": "error", "error_type": "FileReadError", "error_message": "'>' not supported between instances of 'int' and 'str'"}full{"status": "error", "error_type": "FileReadError", "error_message": "'>' not supported between instances of 'int' and 'str'"} |
| 5 | read_file | {
"filepath": "rich/prompt.py"
} | {"status": "ok", "filepath": "rich/prompt.py", "content": "from typing import Any, Generic, List, Optional, TextIO, TypeVar, Union, overload\n\nfrom . import gefull{"status": "ok", "filepath": "rich/prompt.py", "content": "from typing import Any, Generic, List, Optional, TextIO, TypeVar, Union, overload\n\nfrom . import get_console\nfrom .console import Console\nfrom .text import Text, TextType\n\nPromptType = TypeVar(\"PromptType\")\nDefaultType = TypeVar(\"DefaultType\")\n\n\nclass PromptError(Exception):\n \"\"\"Exception base class for prompt related errors.\"\"\"\n\n\nclass InvalidResponse(PromptError):\n \"\"\"Exception to indicate a response was invalid. Raise this within process_response() to indicate an error\n and provide an error message.\n\n Args:\n message (Union[str, Text]): Error message.\n \"\"\"\n\n def __init__(self, message: TextType) -> None:\n self.message = message\n\n def __rich__(self) -> TextType:\n return self.message\n\n\nclass PromptBase(Generic[PromptType]):\n \"\"\"Ask the user for input until a valid response is received. This is the base class, see one of\n the concrete classes for examples.\n\n Args:\n prompt (TextType, optional): Prompt text. Defaults to \"\".\n console (Console, optional): A Console instance or None to use global console. Defaults to None.\n password (bool, optional): Enable password input. Defaults to False.\n choices (List[str], optional): A list of valid choices. Defaults to None.\n case_sensitive (bool, optional): Matching of choices should be case-sensitive. Defaults to True.\n show_default (bool, optional): Show default in prompt. Defaults to True.\n show_choices (bool, optional): Show choices in prompt. Defaults to True.\n \"\"\"\n\n response_type: type = str\n\n validate_error_message = \"[prompt.invalid]Please enter a valid value\"\n illegal_choice_message = (\n \"[prompt.invalid.choice]Please select one of the available options\"\n )\n prompt_suffix = \": \"\n\n choices: Optional[List[str]] = None\n\n def __init__(\n self,\n |
| 6 | read_file | {
"filepath": "rich/prompt.py",
"start_line": "151"
} | {"status": "error", "error_type": "FileReadError", "error_message": "'>' not supported between instances of 'int' and 'str'"}full{"status": "error", "error_type": "FileReadError", "error_message": "'>' not supported between instances of 'int' and 'str'"} |
| 7 | run_command | {
"command": "sed -n '250,310p' rich/prompt.py"
} | {"status": "ok", "stdout": " # return the original choice, not the lower case version\n return_value = self.response_type(\n self.choices[\n [choice.lower() forfull{"status": "ok", "stdout": " # return the original choice, not the lower case version\n return_value = self.response_type(\n self.choices[\n [choice.lower() for choice in self.choices].index(value.lower())\n ]\n )\n return return_value\n\n def on_validate_error(self, value: str, error: InvalidResponse) -> None:\n \"\"\"Called to handle validation error.\n\n Args:\n value (str): String entered by user.\n error (InvalidResponse): Exception instance the initiated the error.\n \"\"\"\n self.console.print(error)\n\n def pre_prompt(self) -> None:\n \"\"\"Hook to display something before the prompt.\"\"\"\n\n @overload\n def __call__(self, *, stream: Optional[TextIO] = None) -> PromptType:\n ...\n\n @overload\n def __call__(\n self, *, default: DefaultType, stream: Optional[TextIO] = None\n ) -> Union[PromptType, DefaultType]:\n ...\n\n def __call__(self, *, default: Any = ..., stream: Optional[TextIO] = None) -> Any:\n \"\"\"Run the prompt loop.\n\n Args:\n default (Any, optional): Optional default value.\n\n Returns:\n PromptType: Processed value.\n \"\"\"\n while True:\n self.pre_prompt()\n prompt = self.make_prompt(default)\n value = self.get_input(self.console, prompt, self.password, stream=stream)\n if value == \"\" and default != ...:\n return default\n try:\n return_value = self.process_response(value)\n except InvalidResponse as error:\n self.on_validate_error(value, error)\n continue\n else:\n return return_value\n\n\nclass Prompt(PromptBase[str]):\n \"\"\"A prompt that returns a str.\n\n Example:\n >>> name = Prompt.ask(\"Enter your |
| 8 | run_command | {
"command": "grep -n \"def on_validate_error\" rich/prompt.py"
} | {"status": "ok", "stdout": "258: def on_validate_error(self, value: str, error: InvalidResponse) -> None:\n", "stderr": "", "exit_code": 0}full{"status": "ok", "stdout": "258: def on_validate_error(self, value: str, error: InvalidResponse) -> None:\n", "stderr": "", "exit_code": 0} |
| 9 | run_command | {
"command": "sed -n '258,266p' rich/prompt.py"
} | {"status": "ok", "stdout": " def on_validate_error(self, value: str, error: InvalidResponse) -> None:\n \"\"\"Called to handle validation error.\n\n Args:\n valfull{"status": "ok", "stdout": " def on_validate_error(self, value: str, error: InvalidResponse) -> None:\n \"\"\"Called to handle validation error.\n\n Args:\n value (str): String entered by user.\n error (InvalidResponse): Exception instance the initiated the error.\n \"\"\"\n self.console.print(error)\n\n", "stderr": "", "exit_code": 0} |
| 10 | run_command | {
"command": "python3 -c \"from rich.console import Console; from rich.prompt import InvalidResponse; console = Console(markup=False); error = InvalidResponse('[red]Error![/red]'); console.print(error); print('Done')\""
} | {"status": "ok", "stdout": "[red]Error![/red]\nDone\n", "stderr": "", "exit_code": 0}full{"status": "ok", "stdout": "[red]Error![/red]\nDone\n", "stderr": "", "exit_code": 0} |
| 11 | run_command | {
"command": "python3 -c \"from rich.console import Console; from rich.prompt import InvalidResponse; console = Console(markup=False); error = InvalidResponse('[red]Error![/red]'); console.print(error, markup=True); print('Done')\""
} | {"status": "ok", "stdout": "Error!\nDone\n", "stderr": "", "exit_code": 0}full{"status": "ok", "stdout": "Error!\nDone\n", "stderr": "", "exit_code": 0} |
| 12 | edit_file | {
"filepath": "rich/prompt.py",
"new_string": " self.console.print(error, markup=True)",
"old_string": " self.console.print(error)"
} | {"status": "ok", "filepath": "rich/prompt.py", "occurrences": 1, "strategy": "exact", "diff": "--- a/rich/prompt.py\n+++ b/rich/prompt.py\n@@ -262,7 +262,7 @@\nfull{"status": "ok", "filepath": "rich/prompt.py", "occurrences": 1, "strategy": "exact", "diff": "--- a/rich/prompt.py\n+++ b/rich/prompt.py\n@@ -262,7 +262,7 @@\n value (str): String entered by user.\n error (InvalidResponse): Exception instance the initiated the error.\n \"\"\"\n- self.console.print(error)\n+ self.console.print(error, markup=True)\n \n def pre_prompt(self) -> None:\n \"\"\"Hook to display something before the prompt.\"\"\"\n", "is_truncated": false} |
| 13 | run_command | {
"command": "python3 -c \"from rich.console import Console; from rich.prompt import InvalidResponse; console = Console(markup=False); error = InvalidResponse('[red]Error![/red]'); console.print(error, markup=True); print('Done')\""
} | {"status": "ok", "stdout": "Error!\nDone\n", "stderr": "", "exit_code": 0}full{"status": "ok", "stdout": "Error!\nDone\n", "stderr": "", "exit_code": 0} |
| 14 | submit_patch | {} | {"status": "ok", "patch_size": 503, "files_changed": 1}full{"status": "ok", "patch_size": 503, "files_changed": 1} |
diff --git a/rich/prompt.py b/rich/prompt.py
index c7cf25ba..ae94d9bb 100644
--- a/rich/prompt.py
+++ b/rich/prompt.py
@@ -262,7 +262,7 @@ class PromptBase(Generic[PromptType]):
value (str): String entered by user.
error (InvalidResponse): Exception instance the initiated the error.
"""
- self.console.print(error)
+ self.console.print(error, markup=True)
def pre_prompt(self) -> None:
"""Hook to display something before the prompt."""
........ [100%] 8 passed in 0.10s