Shofel2_T124_python/venv/lib/python3.10/site-packages/questionary/question.py

135 lines
3.9 KiB
Python
Raw Normal View History

2024-05-25 16:45:07 +00:00
import sys
from typing import Any
import prompt_toolkit.patch_stdout
from prompt_toolkit import Application
from questionary import utils
from questionary.constants import DEFAULT_KBI_MESSAGE
class Question:
"""A question to be prompted.
This is an internal class. Questions should be created using the
predefined questions (e.g. text or password)."""
application: "Application[Any]"
should_skip_question: bool
default: Any
def __init__(self, application: "Application[Any]") -> None:
self.application = application
self.should_skip_question = False
self.default = None
async def ask_async(
self, patch_stdout: bool = False, kbi_msg: str = DEFAULT_KBI_MESSAGE
) -> Any:
"""Ask the question using asyncio and return user response.
Args:
patch_stdout: Ensure that the prompt renders correctly if other threads
are printing to stdout.
kbi_msg: The message to be printed on a keyboard interrupt.
Returns:
`Any`: The answer from the question.
"""
try:
sys.stdout.flush()
return await self.unsafe_ask_async(patch_stdout)
except KeyboardInterrupt:
print("\n{}\n".format(kbi_msg))
return None
def ask(
self, patch_stdout: bool = False, kbi_msg: str = DEFAULT_KBI_MESSAGE
) -> Any:
"""Ask the question synchronously and return user response.
Args:
patch_stdout: Ensure that the prompt renders correctly if other threads
are printing to stdout.
kbi_msg: The message to be printed on a keyboard interrupt.
Returns:
`Any`: The answer from the question.
"""
try:
return self.unsafe_ask(patch_stdout)
except KeyboardInterrupt:
print("\n{}\n".format(kbi_msg))
return None
def unsafe_ask(self, patch_stdout: bool = False) -> Any:
"""Ask the question synchronously and return user response.
Does not catch keyboard interrupts.
Args:
patch_stdout: Ensure that the prompt renders correctly if other threads
are printing to stdout.
Returns:
`Any`: The answer from the question.
"""
if self.should_skip_question:
return self.default
if patch_stdout:
with prompt_toolkit.patch_stdout.patch_stdout():
return self.application.run()
else:
return self.application.run()
def skip_if(self, condition: bool, default: Any = None) -> "Question":
"""Skip the question if flag is set and return the default instead.
Args:
condition: A conditional boolean value.
default: The default value to return.
Returns:
:class:`Question`: `self`.
"""
self.should_skip_question = condition
self.default = default
return self
async def unsafe_ask_async(self, patch_stdout: bool = False) -> Any:
"""Ask the question using asyncio and return user response.
Does not catch keyboard interrupts.
Args:
patch_stdout: Ensure that the prompt renders correctly if other threads
are printing to stdout.
Returns:
`Any`: The answer from the question.
"""
if self.should_skip_question:
return self.default
if not utils.ACTIVATED_ASYNC_MODE:
await utils.activate_prompt_toolkit_async_mode()
if patch_stdout:
with prompt_toolkit.patch_stdout.patch_stdout():
r = self.application.run_async()
else:
r = self.application.run_async()
if utils.is_prompt_toolkit_3():
return await r
else:
return await r.to_asyncio_future() # type: ignore[attr-defined]