Skip to main content

Climax Prompt

Python package for creating cli prompts.

python badge pytest badge ruff badge Sphinx poetry badge PyPI Git GitLab github badge MIT pipeline status

This package exports 2 classes that contain the majority of its primary functionality. The Prompt and StringPrompt classes. The main difference between the 2 is that StringPrompts only processes strings while Prompts can process any arbitrary type.

The StringPrompt.exec_string_input_loop and Prompt.exec_input_loop methods of each class create a loop that prompts a user for input and will reprompt until valid input is inputted and return the inputted string or value (if the string is converted to a non string value).

Usage Examples

StringPrompt Usage Example

from climax.prompt import PromptStringInput, StringPrompt


# string validator gets passed a tuple containing the formatted and original
# unformatted string input
def is_palindrome(string: PromptStringInput) -> str | None:
    return (
        f'Provided input is not a palindrome: "{string.original}"\n'
        if string.formatted != string.formatted[::-1]
        else None
    )


palindrome_prompt = StringPrompt(
    "Input a palindrome...\n",
    is_palindrome,
    formatter=lambda a_string: a_string.strip().lower(),
    ps1=">>> ",
)

# once validation passes the formatted and original unformatted string input
# gets returned
formatted_palindrome_string_input, original_palindrome_string_input: PromptStringInput = palindrome_prompt.exec_string_input_loop()

print(f'You inputted the palindrome: "{formatted_palindrome_string_input}"')

Calling the StringPrompt.exec_string_input_loop method will result in the following process:

  1. The StringPrompt.message to be printed to stdout followed by the StringPrompt.ps1 if set.

  2. The string inputted to stdin then gets passed to the StringPrompt.formatter(str).

  3. The formatted and raw unformatted original input string then gets passed to the StringPrompt.string_validator.

  4. If validation passes (the StringPrompt.string_validator returns None) then both the formatted and original unformatted string input gets returned.

  5. If validation fails (the StringPrompt.string_validator returns a string error message) then the string error message gets printed to stdout and the process is repeated.

When the method in the example above is called this will result in the following prompt in the terminal:

Input a palindrome...
>>> slITher                                   # simulated user input
Provided input is not a palindrome: "slITher" # original unformatted string used in error message
Input a palindrome...
>>> levEl                                     # simulated user input
You inputted the palindrome: "level"          # formatted input used for validation and used in this print statement

Prompt Usage Example

from climax.prompt import Prompt, PromptInput, PromptStringInput


# string validator gets passed a tuple containing the formatted and original
# unformatted string input
def string_is_integer(string: PromptStringInput) -> str | None:
    return None if string.formatted.isdecimal() else f'Provided input is not an integer: "{string.formatted}"\n'


# validator gets passed whatever the string input gets converted to
def is_positive_even_integer(integer: int) -> str | None:
    if integer <= 0:
        return f"Integer isn't positive: {integer}\n"

    if integer % 2 != 0:
        return f"Integer isn't even: {integer}\n"

    return None


positive_even_integer_prompt = Prompt[int](
    "Input a positive even integer: ",
    string_is_integer,
    int,  # can pass any function/lambda that consumes a string and outputs the specified type
    is_positive_even_integer,
    formatter=str.strip,
)

positive_even_integer_prompt_result = positive_even_integer_prompt.exec_input_loop()

if positive_even_integer_prompt_result.conversion_exception:
    print("Error converting input to an int:", positive_even_integer_prompt_result.original_input_string)
else:
    # prompt result value can safely be used in a type safe way after checking there's no
    # conversion exception
    print("You inputted the positive even integer:", positive_even_integer_prompt_result.value)

Calling the Prompt.exec_input_loop method will result in the same process outlined above when StringPrompt.exec_string_input_loop is called, except it performs additional conversion of the string input and validation on that converted string input as outlined below if string input validation passes (otherwise the reprompt process is identical):

  1. The formatted validated string input is passed to the Prompt.converter(str).

  2. If an exception occurs during conversion, then a PromptInput is returned with the original input string and the Exception that was raised.

  3. If conversion succeeds without raising an exception, the string input is then passed to the Prompt.validator.

  4. If validation passes (the Prompt.validator returns None) then a PromptInput containing the original input string and its converted value is returned.

  5. If validation fails (the Prompt.validator returns a string error message) then the error message gets printed to stdout and the process is repeated.

When the method in the example above is called this will result in the following prompt in the terminal:

Input a positive even integer:    sliTHer          # simulated user input
Provided input is not an integer: "slither"        # formatted string input is used in this message
Input a positive even integer: -34                 # simulated user input
Integer isn't positive: -34
Input a positive even integer: 7                   # simulated user input
Integer isn't even: 7
Input a positive even integer: 22                  # simulated user input
You inputted the positive even integer: 22

Installing Package

This package is available on pypi and can be installed via any of the standard methods:

# via poetry
poetry add climax-prompt

# via uv
uv add climax-prompt

# via pip
pip install climax-prompt

Repo

The next sections cover details and info about this git repository. If you're just importing this package as a dependency in a python project then it probably doesn't apply to you. If you clone this repo, especially if you intend to make a pr, then they're relevant.

Tooling Tasks

The repo for this project uses ruff and mypy for linting, ruff for formatting, pytest for testing, and sphinx (with numpydoc) for generating API documentation.

All repo tasks can be executed via the make targets listed below:

  • setup - Installs all package dependencies and pre-commit hook(s). This should be run right after cloning the repo.
  • ruff-check - Runs the ruff checker extended with the isort I config.
  • ruff-format-check - Runs the ruff formatter with the --check option.
  • mypy - Runs the mypy type checker.
  • lint - Runs the ruff-check, ruff-check-format and mypy targets.
  • format - Formats source code with ruff.
  • test - Runs unit tests and test coverage outputting results to stdout.
  • test-html - Generates unit test results and coverage html reports.
  • serve-tests - Generates and serves unit test results and coverage html reports on 127.0.0.1:8000 and 127.0.0.1:8001. Depends on GNU parallel.
  • serve-docs - Generates and serves html API docs on 127.0.0.1:8000.
  • test-xml - Generates test coverage xml reports.
  • readme - Generate source/README.rst by using pandoc to convert the root README.md to rst.

In addition to the make targets listed above, all sphinx make targets are available and valid as well.

Remotes

The primary remote repo for this package is hosted on gitlab, but is also mirrored to github.

MIT License

This package is licensed under the MIT license and can be found in LICENSE.txt.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

climax_prompt-0.2.1.tar.gz (10.6 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

climax_prompt-0.2.1-py3-none-any.whl (11.1 kB view details)

Uploaded Python 3

File details

Details for the file climax_prompt-0.2.1.tar.gz.

File metadata

  • Download URL: climax_prompt-0.2.1.tar.gz
  • Upload date:
  • Size: 10.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.4.3 CPython/3.14.7 Linux/6.12.107+deb13-amd64

File hashes

Hashes for climax_prompt-0.2.1.tar.gz
Algorithm Hash digest
SHA256 1152b2e32e535c13686df6cea1d285bb466a02c7693f03cd23db47d79d4d2c45
MD5 833f5728a8e4b9da3ea5846fe05cd7a8
BLAKE2b-256 75275eeeb1fd2fd290d8b8134c55c8e282b9ccc6b29c089f1c9a0b78e7d9c4e7

See more details on using hashes here.

File details

Details for the file climax_prompt-0.2.1-py3-none-any.whl.

File metadata

  • Download URL: climax_prompt-0.2.1-py3-none-any.whl
  • Upload date:
  • Size: 11.1 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.4.3 CPython/3.14.7 Linux/6.12.107+deb13-amd64

File hashes

Hashes for climax_prompt-0.2.1-py3-none-any.whl
Algorithm Hash digest
SHA256 1b537b31a6020d5dd63882f70638b90d11369143993e80ba26dcdeb5f39f8c57
MD5 1a8fb7d3debebca2161189bfd90efa9f
BLAKE2b-256 1661cd2f023d185562d167101105d0d79712045688934aa7f4c3ae6c43c02461

See more details on using hashes here.

Release history Release notifications | RSS feed

0.2.6

2 files

0.2.5

2 files

0.2.4

2 files

0.2.2

2 files

This release

0.2.1 This release

2 files

0.1.2

2 files

0.1.1

2 files

0.1.0

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page