I think I need to try to explain what Cement is doing, to decide if I want to do it any differently. So, inside the package, we have:
- main.py defines the basic App class, a "testable" version of that class, and a harness for running the app. The separation here seems to be that the app's run method handles the very high-level happy-path behavior, and the harness handles a few aspects of cleanup that can't really be ignored. Due to the way it's structured, I think the bulk of the main() function could be rewritten as a context manager and thereby made testable. I don't know if I want this all in the same module. I have some ideas there that I haven't fully fleshed out.
- templates contains a sample template for presenting output. I hadn't thought of using Jinja in a command-line application, but I like the idea. (I mean, I was thinking of using it in the virtual tabletop thing that this is all supposed to make easier to develop, but that was at a higher level of abstraction, and I haven't done it yet.) I'm looking at the Jinja extension to get some understanding of how this all works. (One thing that occurs to me, is that it would be helpful to define extras_require in the setup command so that users can do like pip install cement[name-of-optional-plugin] and get exactly the packages required for a plugin, even if the precise details may change.) Anyway, the big thing I'd like to figure out how to do with the Jinja extension is to define custom filters. I think I do that by resolving the app's jinja template handler and messing with its env attribute. That has to be done before rendering anything.
- plugins and ext are empty, and core just defines a custom exception type.
- The main business logic lives in controllers, which has a base.py module that defines the command-line interface. What I want in here is a default handler that launches the tasks and takes an argument for specifying "targets", and a handler for listing available targets (default and non-default)
Testing the core logic will require something akin to pytest's helpers that create and populate temporary directories.
Anyway, here are the tickets I need to put in for myself:
- Specify and rework controllers
- Convert the exception handler into a context manager, or just a higher-order function, or setting the app class as a default argument
- Split out the main module into modules defining classes, and try having minimal logic in main
- Write a hook for injecting filters into the template environment
I'll get those in, then publish, then get to bed.