Textualize/rich · warning · InvalidResponse

[prompt.invalid.choice]Please select one of the available op

Error message

[prompt.invalid.choice]Please select one of the available options

What it means

When a Prompt has choices= set, process_response() calls check_choice(value); if the (case-adjusted) input is not among the choices it raises InvalidResponse with illegal_choice_message ('[prompt.invalid.choice]Please select one of the available options'). Like other prompt errors it is caught by ask(), which re-displays the prompt; it surfaces only when process_response is called outside that loop.

Source

Thrown at rich/prompt.py:247

        Args:
            value (str): String typed by user.

        Raises:
            InvalidResponse: If ``value`` is invalid.

        Returns:
            PromptType: The value to be returned from ask method.
        """
        value = value.strip()
        try:
            return_value: PromptType = self.response_type(value)
        except ValueError:
            raise InvalidResponse(self.validate_error_message)

        if self.choices is not None:
            if not self.check_choice(value):
                raise InvalidResponse(self.illegal_choice_message)

            if not self.case_sensitive:
                # return the original choice, not the lower case version
                return_value = self.response_type(
                    self.choices[
                        [choice.lower() for choice in self.choices].index(value.lower())
                    ]
                )
        return return_value

    def on_validate_error(self, value: str, error: InvalidResponse) -> None:
        """Called to handle validation error.

        Args:
            value (str): String entered by user.
            error (InvalidResponse): Exception instance the initiated the error.
        """
        self.console.print(error, markup=True)

View on GitHub (pinned to 9d8f9a372c)

Solutions

  1. Use Prompt.ask(..., choices=[...]) so rich re-prompts on invalid choice automatically.
  2. Pass case_sensitive=False to accept 'YES'/'Yes' for choice 'yes'.
  3. If you call process_response yourself, catch InvalidResponse and loop; or pre-check with prompt.check_choice(value).

Example fix

# before
ans = Prompt.ask('Mode', choices=['auto','manual'], case_sensitive=True)
# user types 'AUTO' -> re-prompt / InvalidResponse if called directly

# after
ans = Prompt.ask('Mode', choices=['auto','manual'], case_sensitive=False)
Defensive patterns

Strategy: validation

Validate before calling

from rich.prompt import Prompt
choices = ['auto', 'manual']
raw = input('> ')
if not Prompt(f'{"mode"}', choices=choices, case_sensitive=False).check_choice(raw):
    raw = choices[0]  # fallback

Try / catch

try:
    p.process_response(raw)
except InvalidResponse as e:
    # show e.text and re-prompt
    ...

Prevention

When it happens

Trigger: Prompt.ask('Proceed', choices=['yes','no','abort']) and the user types 'maybe'; case-sensitive prompt where the user types 'YES' but the choice is 'yes' with case_sensitive=True; calling process_response('bogus') directly.

Common situations: Menu-driven CLIs where users type free text not in the list; forgetting that case_sensitive defaults to True for Prompt (so 'Y' fails against choice 'y'); typos in choice matching when choices are generated dynamically and the offered list differs from choices=.

Related errors


AI-assisted analysis of Textualize/rich@9d8f9a372c (2026-08-15). Data as JSON: /api/errors/ecb4988c8cc15dba. Report an issue: GitHub.