Skip to content

Pillar: Building Blocks for Python Applications🔗

PyPi PyPI - Status Python Versions License

Introduction🔗

Pillar provides resusable components for building command-line applications. No more copy-pasting boilerplate for logging or argparse just to get bare-bone features.

In particular Pillar focusses on providing components for applications that are run as services, background tasks, or scheduled jobs (e.g. cron jobs).

Pillar is currently Alpha software and does not have complete documentation, testing, or implementation of certain features.

Features🔗

  • Config Loading: Automatically collect, parse, and merge config files provided as arguments.
  • Logging: Preconfigured console and file logging.
    • Includes bare-bones logger for when applications are initialising.
  • Modular: Many components are modular so you can re-use them in your applications without being forced to used all of Pillar.
  • Development: fully typed for your static analysis / linting needs

Why use Pillar over Click, Fire, Typer, or Cement?🔗

Tools like Click, Fire, and Typer are focussed on CLI interfaces and how to get the command-line arguments to the code that runs them. Whilst Pillar can be used for extensive CLIs, it is better suited to single purpose applications like cron jobs. That's not to say that it doesn't support command-line arguments, as it still uses and exposes argparse for you to add your own.

Frameworks like Cement are powerful, but leads to a lot of boilerplate when creating lots of small applications. In contrast Pillar provides most of it's core functionality through a single class that your application subclasses from. You are able to customise and plug-and-play many components, but components are also fairly opinioated so that you don't have to remeber to customise them every time.

Quick Start🔗

Follow our Quickstart Guide.

tldr.py
from pillar.application import Application

class MyApplication(Application):
    "Hello World application that prints basic info then exits"

    def main(self):
        self.info(f"hello world! My name is {self.name}")
        self.debug(f"My config is: {self.config}")
        return

if __name__ == "__main__":
    app = MyApplication()
    app.run()

Bugs, Feature Requests etc🔗

Please submit an issue on github.

In the case of bug reports, please help us help you by following best practices 1 2.

In the case of feature requests, please provide background to the problem you are trying to solve so to help find a solution that makes the most sense for the library as well as your usecase.

Contributing🔗

I am still working through open source licencing and contributing, so not taking PRs at this point in time. Instead raise and issue and I'll try get to it as soon a feasible.

Licence🔗

This project is licenced under the MIT Licence - see LICENCE.

This project includes other open source licenced software - see NOTICE.

Authors🔗

A project by Nicholas Hairs - www.nicholashairs.com.