staged-script
Python is an ideal language for certain types of infrastructure
automation. Automating what a user does manually often involves walking
through a series of stages. A user may wish to run all the stages in
series, or perhaps only a subset, and depending on how things go,
certain stages may need to be retried. Once the script finishes
running, it’d be ideal if it could tell the user exactly what was run,
for the sake of easing replicability. staged-script aims to ease
the development such automation scripts. It’s easy to get started with,
but also provides significant power-user functionality for those who
need it.
Installation
To get up and running with staged-script, simply
python3 -m pip install staged-script
Usage
Once the package is installed, you can simply
example/ex_0_the_basics.py 1import sys
2
3from staged_script import StagedScript
4
5
6class MyScript(StagedScript):
7 @StagedScript.stage("hello", "Greeting the user")
8 def say_hello(self) -> None:
9 self.run("echo 'Hello World'", shell=True)
10
11 @StagedScript.stage("goodbye", "Bidding farewell")
12 def say_goodbye(self) -> None:
13 self.run("echo 'Goodbye World'", shell=True)
14
15 def main(self, argv: list[str]) -> None:
16 self.parse_args(argv)
17 try:
18 self.say_hello()
19 self.say_goodbye()
20 finally:
21 self.print_script_execution_summary()
22
23
24if __name__ == "__main__":
25 my_script = MyScript({"hello", "goodbye"})
26 my_script.main(sys.argv[1:])
Executing the script then yields
>>> ./ex_0_the_basics.py --stage hello goodbye
[07:34:19] ╭─────────────────────────────────────────────╮ staged_script.py:937
│ Greeting the user │
╰─────────────────────────────────────────────╯
Executing: echo 'Hello World' staged_script.py:827
Hello World
`hello` stage duration: 0:00:00.020772 staged_script.py:476
╭─────────────────────────────────────────────╮ staged_script.py:937
│ Bidding farewell │
╰─────────────────────────────────────────────╯
Executing: echo 'Goodbye World' staged_script.py:827
Goodbye World
`goodbye` stage duration: 0:00:00.012504 staged_script.py:476
───────────────── ex_0_the_basics.py Script Execution Summary ─────────────────
staged_script.py:920
➤ Ran the following:
ex_0_the_basics.py \
--stage hello goodbye \
--hello-retry-attempts 0 \
--hello-retry-delay 0 \
--hello-retry-timeout 60 \
--goodbye-retry-attempts 0 \
--goodbye-retry-delay 0 \
--goodbye-retry-timeout 60
➤ Commands executed:
echo 'Hello World'
echo 'Goodbye World'
➤ Timing results:
┏━━━━━━━━━┳━━━━━━━━━━━━━━━━┓
┃ Stage ┃ Duration ┃
┡━━━━━━━━━╇━━━━━━━━━━━━━━━━┩
│ hello │ 0:00:00.020772 │
│ goodbye │ 0:00:00.012504 │
├─────────┼────────────────┤
│ Total │ 0:00:00.035295 │
└─────────┴────────────────┘
➤ Script result:
Success
─────────────── End ex_0_the_basics.py Script Execution Summary ───────────────
For more detailed usage information, see the Examples page. For implementation details, see the Reference documentation.
Contributing
The source repository for this module is on GitHub. See the project’s README and contributing guidelines for details on how to interact with the project.
Inspiration
Aspects of this functionality were inspired by the SPiFI Jenkins Pipeline plugin and the shell-logger Python package.