Guide 1: Hello World
This guide creates the smallest useful quickli application: a greeting tool that
accepts a name and an optional flag to print the message in uppercase.
You will learn how to:
- create an
Applicationwith a description - register an entrypoint using
@app.entrypoint - add a positional
Argument - add a boolean
Optionflag - run the application from the command line
The full example
Save the following file as hello.py:
from __future__ import annotations
from quickli import Application, Argument, Option
app = Application(
name="hello",
description="Greet a person from the command line.",
)
@app.entrypoint(
help_text="Print a greeting.",
arguments=[Argument("name", help_text="Name to greet.")],
options=[
Option(
"uppercase",
short_name="u",
is_flag=True,
help_text="Print the greeting in uppercase.",
),
],
)
def greet(name: str, uppercase: bool = False) -> str:
message = f"Hello, {name}!"
return message.upper() if uppercase else message
if __name__ == "__main__":
sys.exit(app.main())
Run it
python hello.py Ada
# Hello, Ada!
python hello.py Ada --uppercase
# HELLO, ADA!
python hello.py Ada -u
# HELLO, ADA!
Line-by-line explanation
Imports
from quickli import Application, Argument, Option
You only need to import the three classes you use. quickli keeps its public API small
and explicit.
Creating the application
app = Application(
name="hello",
description="Greet a person from the command line.",
)
Application is the root container. name is used in help output. description appears
below the usage line when you run the tool without arguments.
Registering the entrypoint
@app.entrypoint(
help_text="Print a greeting.",
arguments=[Argument("name", help_text="Name to greet.")],
options=[
Option(
"uppercase",
short_name="u",
is_flag=True,
help_text="Print the greeting in uppercase.",
),
],
)
def greet(name: str, uppercase: bool = False) -> str:
...
@app.entrypoint is used for commandless applications — the application has one purpose,
so there is no need for a command name.
help_textappears in the generated usage output.argumentsis a list ofArgumentinstances in positional order.optionsis a list ofOptioninstances.
The Argument constructor
Argument("name", help_text="Name to greet.")
Argument takes a positional name as its first argument. This name must match the
corresponding function parameter. By default, arguments are required. To make an argument
optional, pass required=False and provide a default.
The Option constructor
Option(
"uppercase",
short_name="u",
is_flag=True,
help_text="Print the greeting in uppercase.",
)
"uppercase"becomes--uppercaseon the command line.short_name="u"adds the-ushort form.is_flag=Truemeans the option is boolean: present →True, absent →False.- The function parameter must match the option name with hyphens replaced by underscores
(
uppercase→uppercase).
The handler function
def greet(name: str, uppercase: bool = False) -> str:
message = f"Hello, {name}!"
return message.upper() if uppercase else message
The handler receives parsed values directly. quickli matches argument and option names
to parameter names. The default value for uppercase corresponds to the option being
absent.
The handler returns a string. Application.main() prints that return value for normal
successful runs.
The entry point
if __name__ == "__main__":
sys.exit(app.main())
Application.main() is the simplest executable entry point. It reads sys.argv[1:],
prints normal results, reports quickli runtime errors, and returns an exit code.
Application.run(argv) still accepts explicit tokens when you want that lower-level,
test-friendly boundary.
Application.run() also reads sys.argv[1:] by default when called without arguments.
Pass an explicit list to override or set auto_sys_argv=False to disable automatic reading.
Explore help output
Run without arguments to see the generated help:
python hello.py
quickli generates usage text from the registered arguments, options, and help strings.
What to try next
- Add a second option (for example
--shout) and change the message format. - Make the
nameargument optional withrequired=Falseanddefault="world". - Read Guide 2: File Viewer to learn about global options, multiple file arguments, and path validation.
