Application

Application with bindings for commands

The application object handles all of the initial configuration to setup the run-time environment.

Quick demo:

>>> from pyapp.app import CliApplication

>>> app = CliApplication()

>>> @app.command()
>>> def hello(*, verbose: bool):
...     if verbose:
...         print("Being verbose!")
...     print("Hello")

>>> if __name__ == '__main__':
...     app.dispatch()

This example provides an application with a command hello that takes an optional verbose flag. The framework also provides help, configures and loads settings (using pyapp.conf), an interface to the checks framework and configures the Python logging framework.

There are however a few more things that are required to get this going. The CliApplication class expects a certain structure of your application to allow for it’s (customisable) defaults to be applied.

Your application can have one of two structures

An application:

my_app/__init__.py          # Include a __version__ variable
       __main__.py          # This is where the quick demo is located
       default_settings.py  # The default settings file
       checks.py            # Optional checks file

A single script:

my_app.py                   # A script that contains the `CliApplication`

Generation of CLI from command Signature

New in version 4.4.

As of pyApp 4.4 command functions can supply all required arguments in the function signature.

As an example consider the command function:

@app.command
def my_command(
    arg1: str,
    *,
    arg2: bool= Arg(help="Enable the argilizer"),
    arg3: int = 42,
    arg4: str = Arg("-a", choices=("foo", "bar"), default="foo")
):
    ...

This translates into the following on the CLI:

> python -m my_app my_command --help
usage: my_app my_command [-h] ARG1 [--arg2] [--arg3 ARG3]
                         [--arg4 {foo,bar}]

positional arguments:
  ARG1

optional arguments:
  -h, --help  show this help message and exit
  --arg2    Enable the argilizer
  --arg3
  --arg4 {foo,bar}

The following types are supported as arguments:

  • Basic types eg int, str, float, this covers any type that can be provided to argparse in the type field.

  • bool, this is made into an argparse store_true action.

  • Enum types using the pyApp EnumAction.

  • Generic types
    • Mapping/Dict as well as a basic dict for Key/Value pairs

    • Sequence/List for typed sequences, nargs="+" for positional arguments of action="append" for optional.

    • Tuple for typed sequences of a fixed size eg nargs=len(tuple). Only the first type is used, the others are ignored.

  • FileType from argparse.

Tip

Too get access to the parse results from argparse provide a vairable with the type pyapp.app.CommandOptions.

CliApplication

class pyapp.app.CliApplication(root_module=None, *, prog: Optional[str] = None, description: Optional[str] = None, epilog: Optional[str] = None, version: Optional[str] = None, ext_white_list: Optional[Sequence[str]] = None, ext_allow_list: Optional[Sequence[str]] = None, application_settings: Optional[str] = None, application_checks: Optional[str] = None, env_settings_key: Optional[str] = None, env_loglevel_key: Optional[str] = None)[source]

Application interface that provides a CLI interface.

Parameters
  • root_module – The root module for this application (used for discovery of other modules)

  • prog – Name of your application; defaults to sys.argv[0]

  • description – A description of your application for –help.

  • version – Specify a specific version; defaults to getattr(root_module, ‘__version__’)

  • ext_white_list – Sequence if extensions that are white listed; default is None or all extensions.

  • application_settings – The default settings for this application; defaults to root_module.default_settings

  • application_checks – Location of application checks file; defaults to root_module.checks if it exists.

  • env_settings_key – Key used to define settings file in environment.

  • env_loglevel_key – Key used to define log level in environment

command(handler: Optional[Union[Callable[, Optional[int]], Callable[argparse.Namespace, Optional[int]], Callable[, Awaitable[Optional[int]]], Callable[argparse.Namespace, Awaitable[Optional[int]]]]] = None, *, name: Optional[str] = None, aliases: Sequence[str] = (), help_text: Optional[str] = None)pyapp.app.arguments.CommandProxy

Decorator for registering handlers.

Parameters
  • handler – Handler function

  • name – Optional name to use for CLI; defaults to the function name.

  • aliases – A sequence a name aliases for this command command.

  • help_text – Information provided to the user if help is invoked; default is taken from the handlers doc string.

Changed in version 4.3: Async handlers supported.

create_command_group(name: str, *, aliases: Sequence[str] = (), help_text: Optional[str] = None)pyapp.app.arguments.CommandGroup

Create a command group

Parameters
  • name – Name of the command group

  • aliases – A sequence a name aliases for this command group.

  • help_text – Information provided to the user if help is invoked.

default(handler: Union[Callable[, Optional[int]], Callable[argparse.Namespace, Optional[int]], Callable[, Awaitable[Optional[int]]], Callable[argparse.Namespace, Awaitable[Optional[int]]]])

Decorator for registering a default handler.

Changed in version 4.3: Async handlers supported.

dispatch(args: Optional[Sequence[str]] = None)None[source]

Dispatch command to registered handler.

Arguments

Any command associated with a pyApp application can be expanded with arguments. Arguments are a set of decorators that utilise argparse to simplify the process of accepting and validating input/flags for commands.

pyapp.app.arguments.argument(*name_or_flags, action: str = None, nargs: Union[int, str] = None, const: Any = None, default: Any, type: Type[Any] = None, choices: Sequence[Any] = None, required: bool = None, help_text: str = None, metavar: str = None, dest: str = None)

Decorator for adding arguments to a handler.

This decorator can be used before or after the handler registration decorator CliApplication.command() has been used.

Parameters
  • name_or_flags – Either a name or a list of option strings, e.g. foo or -f, –foo.

  • action – The basic type of action to be taken when this argument is encountered at the command line.

  • nargs – The number of command-line arguments that should be consumed.

  • const – A constant value required by some action and nargs selections.

  • default – The value produced if the argument is absent from the command line.

  • type – The type to which the command-line argument should be converted.

  • choices – A container of the allowable values for the argument.

  • required – Whether or not the command-line option may be omitted (optionals only).

  • help_text – A brief description of what the argument does.

  • metavar – A name for the argument in usage messages.

  • dest – The name of the attribute to be added to the object returned by parse_args().

Argument Types

Additional “types” to handle common CLI situations.

class pyapp.app.argument_types.RegexType(regex, message: Optional[str] = None)[source]

Factory for validating string options against a regular expression.

Instances of RegexType are typically passed as type= arguments to the ArgumentParser add_argument() method or pyApp argument decorator.

Parameters
  • regex – Regular expression string (or pre-compiled expression)

  • message – Optional message if validation fails, defaults to a simple fallback.

Example of use:

@app.command
@argument("--alpha", type=RegexType(r"[a-z]+"))
def my_command(args: Namespace):
    print(args.option)

From CLI:

> my_app m_command --alpha abc
abc

New in version 4.2.

Argument Actions

Additional actions to handle common CLI situations.

Key/Value Arguments

class pyapp.app.argument_actions.KeyValueAction(**kwargs)[source]

Action that accepts key/value pairs and appends them to a dictionary.

Example of use:

@app.command
@argument("--option", action=KeyValueAction)
def my_command(args: Namespace):
    print(args.option)

From CLI:

> my_app m_command --option a=foo --option b=bar
{'a': 'foo', 'b': 'bar'}

Enum types

class pyapp.app.argument_actions.EnumValue(**kwargs)[source]

Action to use an Enum as the type of an argument. In this mode the Enum is reference by value.

The choices are automatically generated for help.

Example of use:

class Colour(Enum):
    Red = "red"
    Green = "green"
    Blue = "blue"

@app.command
@argument("--colour", type=Colour, action=EnumValue)
def my_command(args: Namespace):
    print(args.colour)

From CLI:

> my_app m_command --colour red
Colour.Red

New in version 4.2.

class pyapp.app.argument_actions.EnumName(**kwargs)[source]

Action to use an Enum as the type of an argument. In this mode the Enum is reference by name.

The choices are automatically generated for help.

Example of use:

class Colour(Enum):
    Red = "red"
    Green = "green"
    Blue = "blue"

@app.command
@argument("--colour", type=Colour, action=EnumName)
def my_command(args: Namespace):
    print(args.colour)

From CLI:

> my_app m_command --colour Red
Colour.Red

New in version 4.2.