Skip to content

Commit e4ab25f

Browse files
authored
Added a couple simple example for using tmux or byobu to launch cmd2 applications (#1399)
* Added a couple simple example shell scripts demonstrating how to use tmux or byobu to launch a cmd2 application in a terminal multiplexer along with another application such as a shell. One example uses windows/tabs and the other uses a split screen mode. * Improved the documentation for all cmd2 examples * Added info on the tmux examples to the examples/README.md * Added a link to the example applications from top-level README * Fix spelling and grammar errors
1 parent 9d3f227 commit e4ab25f

File tree

8 files changed

+207
-38
lines changed

8 files changed

+207
-38
lines changed

README.md

Lines changed: 28 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -39,30 +39,30 @@ The price we pay for beautifully colored displays is complexity required to aggr
3939
The `cmd2` framework provides a great mixture of both worlds. Application designers can easily create complex applications and rely on the cmd2 library to offer effortless user facing help and extensive tab completion.
4040
When users become comfortable with functionality, cmd2 turns into a feature rich library enabling a smooth transition to full automation. If designed with enough forethought, a well implemented cmd2 application can serve as a boutique workflow tool. `cmd2` pulls off this flexibility based on two pillars of philosophy:
4141

42-
- Tab Completion
43-
- Automation Transition
42+
- Tab Completion
43+
- Automation Transition
4444

4545
## Philosophy
4646

4747
<a href="https://imgflip.com/i/63h03x"><img src="https://i.imgflip.com/63h03x.jpg" title="made at imgflip.com" width="70%" height="%70"/></a>
4848

4949
Deep extensive tab completion and help text generation based on the argparse library create the first pillar of 'ease of command discovery'. The following is a list of features in this category.
5050

51-
- Great tab completion of commands, subcommands, file system paths, and shell commands.
52-
- Custom tab completion for user designed commands via simple function overloading.
53-
- Tab completion from `persistent_history_file` sources added with very little friction.
54-
- Automatic tab completion of `argparse` flags and optional arguments.
55-
- Path completion easily enabled.
56-
- When all else fails, custom tab completion based on `choices_provider` can fill any gaps.
51+
- Great tab completion of commands, subcommands, file system paths, and shell commands.
52+
- Custom tab completion for user designed commands via simple function overloading.
53+
- Tab completion from `persistent_history_file` sources added with very little friction.
54+
- Automatic tab completion of `argparse` flags and optional arguments.
55+
- Path completion easily enabled.
56+
- When all else fails, custom tab completion based on `choices_provider` can fill any gaps.
5757

5858
<a href="https://imgflip.com/i/66t0y0"><img src="https://i.imgflip.com/66t0y0.jpg" title="made at imgflip.com" width="70%" height="70%"/></a>
5959

6060
cmd2 creates the second pillar of 'ease of transition to automation' through alias/macro creation, command line argument parsing and execution of cmd2 scripting.
6161

62-
- Flexible alias and macro creation for quick abstraction of commands.
63-
- Text file scripting of your application with `run_script` (`@`) and `_relative_run_script` (`@@`)
64-
- Powerful and flexible built-in Python scripting of your application using the `run_pyscript` command
65-
- Transcripts for use with built-in regression can be automatically generated from `history -t` or `run_script -t`
62+
- Flexible alias and macro creation for quick abstraction of commands.
63+
- Text file scripting of your application with `run_script` (`@`) and `_relative_run_script` (`@@`)
64+
- Powerful and flexible built-in Python scripting of your application using the `run_pyscript` command
65+
- Transcripts for use with built-in regression can be automatically generated from `history -t` or `run_script -t`
6666

6767
## Installation
6868

@@ -88,14 +88,17 @@ The best way to learn the cmd2 api is to delve into the example applications loc
8888

8989
## Tutorials
9090

91-
- PyOhio 2019 presentation:
92-
- [video](https://www.youtube.com/watch?v=pebeWrTqIIw)
93-
- [slides](https://github.com/python-cmd2/talks/blob/master/PyOhio_2019/cmd2-PyOhio_2019.pdf)
94-
- [example code](https://github.com/python-cmd2/talks/tree/master/PyOhio_2019/examples)
95-
- [Cookiecutter](https://github.com/cookiecutter/cookiecutter) Templates from community
96-
- Basic cookiecutter template for cmd2 application : https://github.com/jayrod/cookiecutter-python-cmd2
97-
- Advanced cookiecutter template with external plugin support : https://github.com/jayrod/cookiecutter-python-cmd2-ext-plug
98-
- [Example Applications](https://github.com/jayrod/cmd2-example-apps)
91+
- PyOhio 2019 presentation:
92+
- [video](https://www.youtube.com/watch?v=pebeWrTqIIw)
93+
- [slides](https://github.com/python-cmd2/talks/blob/master/PyOhio_2019/cmd2-PyOhio_2019.pdf)
94+
- [example code](https://github.com/python-cmd2/talks/tree/master/PyOhio_2019/examples)
95+
- [Cookiecutter](https://github.com/cookiecutter/cookiecutter) Templates from community
96+
- Basic cookiecutter template for cmd2 application : https://github.com/jayrod/cookiecutter-python-cmd2
97+
- Advanced cookiecutter template with external plugin support : https://github.com/jayrod/cookiecutter-python-cmd2-ext-plug
98+
- [cmd2 example applications](https://github.com/python-cmd2/cmd2/tree/master/examples)
99+
- Basic cmd2 examples to demonstrate how to use various features
100+
- [Advanced Examples](https://github.com/jayrod/cmd2-example-apps)
101+
- More complex examples that demonstrate more featuers about how to put together a complete application
99102

100103
## Hello World
101104

@@ -122,11 +125,11 @@ if __name__ == '__main__':
122125

123126
If you think you've found a bug, please first read through the open [Issues](https://github.com/python-cmd2/cmd2/issues). If you're confident it's a new bug, go ahead and create a new GitHub issue. Be sure to include as much information as possible so we can reproduce the bug. At a minimum, please state the following:
124127

125-
- `cmd2` version
126-
- Python version
127-
- OS name and version
128-
- What you did to cause the bug to occur
129-
- Include any traceback or error message associated with the bug
128+
- `cmd2` version
129+
- Python version
130+
- OS name and version
131+
- What you did to cause the bug to occur
132+
- Include any traceback or error message associated with the bug
130133

131134
## Projects using cmd2
132135

docs/examples/examples.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
# List of cmd2 examples
2+
3+
{%
4+
include-markdown "../../examples/README.md"
5+
%}

docs/examples/index.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,8 @@
22

33
<!--intro-start-->
44

5-
- [First Application](first_app.md)
6-
- [Alternate Event Loops](alternate_event_loops.md)
5+
- [First Application](first_app.md)
6+
- [Alternate Event Loops](alternate_event_loops.md)
7+
- [List of cmd2 examples](examples.md)
78

89
<!--intro-end-->

examples/README.md

Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
# cmd2 Examples
2+
3+
The [examples](https://github.com/python-cmd2/cmd2/tree/master/examples) directory within the `cmd2` repository contains a number of simple self-contained examples which each demonstrate a few particular features of `cmd2`. None of them are representative of a full real-world complex `cmd2` application, if you are looking for that then see [Projects using cmd2](https://github.com/python-cmd2/cmd2?tab=readme-ov-file#projects-using-cmd2).
4+
5+
## List of cmd2 examples
6+
7+
Here is the list of examples in alphabetical order by filename along with a brief description of each:
8+
9+
- [alias_startup.py](https://github.com/python-cmd2/cmd2/blob/master/examples/alias_startup.py)
10+
- Demonstrates how to add custom command aliases and how to run an initialization script at startup
11+
- [arg_decorators.py](https://github.com/python-cmd2/cmd2/blob/master/examples/arg_decorators.py)
12+
- Demonstrates how to use the `cmd2.with_argparser` decorator to specify command arguments using [argparse](https://docs.python.org/3/library/argparse.html)
13+
- [arg_print.py](https://github.com/python-cmd2/cmd2/blob/master/examples/arg_print.py)
14+
- Demonstrates how arguments and options get parsed and passed to commands and shows how shortcuts work
15+
- [argparse_completion.py](https://github.com/python-cmd2/cmd2/blob/master/examples/argparse_completion.py)
16+
- Shows how to integrate tab-completion with argparse-based commands
17+
- [async_printing.py](https://github.com/python-cmd2/cmd2/blob/master/examples/async_printing.py)
18+
- Shows how to asynchronously print alerts, update the prompt in realtime, and change the window title
19+
- [basic.py](https://github.com/python-cmd2/cmd2/blob/master/examples/basic.py)
20+
- Shows how to add a command, add help for it, and create persistent command history for your application
21+
- [basic_completion.py](https://github.com/python-cmd2/cmd2/blob/master/examples/basic_completion.py)
22+
- Show how to enable custom tab completion by assigning a completer function to `do_*` commands
23+
- [cmd2_as_argument.py](https://github.com/python-cmd2/cmd2/blob/master/examples/cmd_as_argument.py)
24+
- Demonstrates how to accept and parse command-line arguments when invoking a cmd2 application
25+
- [colors.py](https://github.com/python-cmd2/cmd2/blob/master/examples/colors.py)
26+
- Show various ways of using colorized output within a cmd2 application
27+
- [custom_parser.py](https://github.com/python-cmd2/cmd2/blob/master/examples/custom_parser.py)
28+
- Demonstrates how to create your own customer `Cmd2ArgumentParser`; used by the `override_parser.py` example
29+
- [decorator_example.py](https://github.com/python-cmd2/cmd2/blob/master/examples/decorator_example.py)
30+
- Shows how to use cmd2's various argparse decorators to processes command-line arguments
31+
- [default_categories.py](https://github.com/python-cmd2/cmd2/blob/master/examples/default_categories.py)
32+
- Demonstrates usage of `@with_default_category` decorator to group and categorize commands and `CommandSet` use
33+
- [dynamic_commands.py](https://github.com/python-cmd2/cmd2/blob/master/examples/dynamic_commands.py)
34+
- Shows how `do_*` commands can be dynamically created programatically at runtime
35+
- [environment.py](https://github.com/python-cmd2/cmd2/blob/master/examples/environment.py)
36+
- Shows how to create custom `cmd2.Settable` parameters which serve as internal environment variables
37+
- [event_loops.py](https://github.com/python-cmd2/cmd2/blob/master/examples/event_loops.py)
38+
- Shows how to integrate a `cmd2` application with an external event loop which isn't managed by `cmd2`
39+
- [example.py](https://github.com/python-cmd2/cmd2/blob/master/examples/example.py)
40+
- This example is intended to demonstrate `cmd2's` build-in transcript testing capability
41+
- [exit_code.py](https://github.com/python-cmd2/cmd2/blob/master/examples/exit_code.py)
42+
- Show how to emit a non-zero exit code from your `cmd2` application when it exits
43+
- [first_app.py](https://github.com/python-cmd2/cmd2/blob/master/examples/first_app.py)
44+
- Short application that demonstrates 8 key features: Settings, Commands, Argument Parsing, Generating Output, Help, Shortcuts, Multiple Commands, and History
45+
- [hello_cmd2.py](https://github.com/python-cmd2/cmd2/blob/master/examples/hello_cmd2.py)
46+
- Completely bare-bones `cmd2` application suitable for rapid testing and debugging of `cmd2` itself
47+
- [help_categories.py](https://github.com/python-cmd2/cmd2/blob/master/examples/help_categories.py)
48+
- Demonstrates command categorization and its impact on the output of the built-in `help` command
49+
- [hooks.py](https://github.com/python-cmd2/cmd2/blob/master/examples/hooks.py)
50+
- Shows how to use various `cmd2` application lifecycle hooks
51+
- [initialization.py](https://github.com/python-cmd2/cmd2/blob/master/examples/initialization.py)
52+
- Shows how to colorize output, use multiline command, add persistent history, and more
53+
- [migrating.py](https://github.com/python-cmd2/cmd2/blob/master/examples/migrating.py)
54+
- A simple `cmd` application that you can migrate to `cmd2` by changing one line
55+
- [modular_commands_basic.py](https://github.com/python-cmd2/cmd2/blob/master/examples/modular_commands_basic.py)
56+
- Demonstrates based `CommandSet` usage
57+
- [modular_commands_dynamic.py](https://github.com/python-cmd2/cmd2/blob/master/examples/modular_commands_dynamic.py)
58+
- Demonstrates dynamic `CommandSet` loading and unloading
59+
- [modular_commands_main.py](https://github.com/python-cmd2/cmd2/blob/master/examples/modular_commands_main.py)
60+
- Complex example demonstrating a variety of methods to load `CommandSets` using a mix of command decorators
61+
- [modular_subcommands.py](https://github.com/python-cmd2/cmd2/blob/master/examples/modular_subcommands.py)
62+
- Shows how to dynamically add and remove subcommands at runtime using `CommandSets`
63+
- [override-parser.py](https://github.com/python-cmd2/cmd2/blob/master/examples/override_parser.py)
64+
- Shows how to override cmd2's default `Cmd2ArgumentParser` with your own customer parser class
65+
- [paged_output.py](https://github.com/python-cmd2/cmd2/blob/master/examples/paged_output.py)
66+
- Shows how to use output pagination within `cmd2` apps via the `ppaged` method
67+
- [persistent_history.py](https://github.com/python-cmd2/cmd2/blob/master/examples/persistent_history.py)
68+
- Shows how to enable persistent history in your `cmd2` application
69+
- [pirate.py](https://github.com/python-cmd2/cmd2/blob/master/examples/pirate.py)
70+
- Demonstrates many features including colorized output, multiline commands, shorcuts, defaulting to shell, etc.
71+
- [python_scripting.py](https://github.com/python-cmd2/cmd2/blob/master/examples/python_scripting.py)
72+
- Shows how cmd2's built-in `run_pyscript` command can provide advanced Python scripting of cmd2 applications
73+
- [read_input.py](https://github.com/python-cmd2/cmd2/blob/master/examples/read_input.py)
74+
- Demonstrates the various ways to call `cmd2.Cmd.read_input()` for input history and tab completion
75+
- [remove_builtin_commands.py](https://github.com/python-cmd2/cmd2/blob/master/examples/remove_builtin_commands.py)
76+
- Shows how to remove any built-in cmd2 commands you do not want to be present in your cmd2 application
77+
- [remove_settable.py](https://github.com/python-cmd2/cmd2/blob/master/examples/remove_settable.py)
78+
- Shows how to remove any of the built-in cmd2 `Settables` you do not want in your cmd2 application
79+
- [subcommands.py](https://github.com/python-cmd2/cmd2/blob/master/examples/subcommands.py)
80+
- Shows how to use `argparse` to easily support sub-commands within your cmd2 commands
81+
- [table_creation.py](https://github.com/python-cmd2/cmd2/blob/master/examples/table_creation.py)
82+
- Contains various examples of using cmd2's table creation capabilities
83+
- [tmux_launch.sh](https://github.com/python-cmd2/cmd2/blob/master/examples/tmux_launch.sh)
84+
- Shell script that launches two applications using tmux in different windows/tabs
85+
- [tmux_split.sh](https://github.com/python-cmd2/cmd2/blob/master/examples/tmux_split.sh)
86+
- Shell script that launches two applications using tmux in a split pane view
87+
- [unicode_commands.py](https://github.com/python-cmd2/cmd2/blob/master/examples/unicode_commands.py)
88+
- Shows that cmd2 supports unicode everywhere, including within command names

examples/migrating.py

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,11 @@
11
#!/usr/bin/env python
22
# coding=utf-8
33
"""
4-
A sample application for cmd which can be used to show how to migrate to cmd2.
4+
A sample cmd application that shows how to trivially migrate a cmd application to use cmd2.
55
"""
66

7-
import cmd
7+
# import cmd2 as cmd
8+
import cmd # Comment this line and uncomment the one above to migrate to cmd2
89
import random
910

1011

examples/tmux_launch.sh

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
#!/usr/bin/env zsh
2+
3+
# This script launches two applications using tmux in different windows/tabs.
4+
# The user is required to enter the name of at least the first application.
5+
# If the second isn't provided, then the user's default shell is launched for this.
6+
# You must have tmux installed and that can be done using your operating system's package manager.
7+
#
8+
# See the tmux Uncyclo for info on how to use it: https://github.com/tmux/tmux/wiki.
9+
# To shift focus between different windows in tmux use Ctrl-b followed by l (lowercase "L").
10+
#
11+
# NOTE: If you have byobu installed, it is a wrapper around tmux and will likely run instead of tmux.
12+
# For info on how to use Byobu, see: https://www.byobu.org/
13+
# To shift focus between windows/tabs in byobu, simply hit F3.
14+
15+
# Function to print in red
16+
print_red() {
17+
echo -e "\e[31m$*\e[0m"
18+
}
19+
20+
if [ $# -eq 0 ];
21+
then
22+
print_red "No arguments supplied and this script requires at least one"
23+
exit 1
24+
fi
25+
26+
FIRST_COMMAND=$1
27+
28+
if [ $# -eq 1 ]
29+
then
30+
SECOND_COMMAND=$SHELL
31+
else
32+
SECOND_COMMAND=$2
33+
fi
34+
35+
tmux new-session -s "tmux window demo" -n "$FIRST_COMMAND" "$FIRST_COMMAND ;read" \; \
36+
new-window -n "$SECOND_COMMAND" "$SECOND_COMMAND ; read" \; previous-window

examples/tmux_split.sh

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
#!/usr/bin/env zsh
2+
3+
# This script launches two applications using byobu in different tabs.
4+
# The user is required to enter the name of at least the first application.
5+
# If the second isn't provided, then the user's default shell is launched for this.
6+
#
7+
# byobu must be installed for this script to work and you can install it using your
8+
# operating system package manager. For info on how to use Byobu, see: https://www.byobu.org/
9+
#
10+
# To shift focus between tabs in byobu, just hit F3.
11+
12+
# Function to print in red
13+
print_red() {
14+
echo -e "\e[31m$*\e[0m"
15+
}
16+
17+
if [ $# -eq 0 ];
18+
then
19+
print_red "No arguments supplied and this script requires at least one"
20+
exit 1
21+
fi
22+
23+
FIRST_COMMAND=$1
24+
25+
if [ $# -eq 1 ]
26+
then
27+
SECOND_COMMAND=$SHELL
28+
else
29+
SECOND_COMMAND=$2
30+
fi
31+
32+
tmux new-session -s "tmux split pane demo" "$FIRST_COMMAND ; read" \; \
33+
split-window "$SECOND_COMMAND ; read" \; \
34+
select-layout even-vertical

mkdocs.yml

Lines changed: 10 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
site_name: cmd2
33
site_description: cmd2 - quickly build feature-rich and user-friendly interactive command line applications in Python.
44
site_dir: build/html
5-
site_url: !ENV [READTHEDOCS_CANONICAL_URL, https://cmd2.readthedocs.io/]
5+
site_url: !ENV [READTHEDOCS_CANONICAL_URL, https://cmd2.readthedocs.io/]
66

77
# Repository
88
repo_name: cmd2
@@ -72,18 +72,18 @@ plugins:
7272
python:
7373
options:
7474
extensions:
75-
- griffe_typingdoc
75+
- griffe_typingdoc
7676
show_root_heading: true
7777
show_if_no_docstring: true
7878
preload_modules:
79-
- argparse
80-
- cmd
79+
- argparse
80+
- cmd
8181
inherited_members: true
8282
members_order: source
8383
separate_signature: true
8484
unwrap_annotated: true
8585
filters:
86-
- '!^_'
86+
- "!^_"
8787
merge_init_into_class: true
8888
docstring_section_style: spacy
8989
signature_crossrefs: true
@@ -122,9 +122,9 @@ markdown_extensions:
122122
- pymdownx.smartsymbols
123123
- pymdownx.superfences:
124124
custom_fences:
125-
- name: mermaid
126-
class: mermaid
127-
format: !!python/name:pymdownx.superfences.fence_code_format
125+
- name: mermaid
126+
class: mermaid
127+
format: !!python/name:pymdownx.superfences.fence_code_format
128128
- pymdownx.tabbed:
129129
alternate_style: true
130130

@@ -189,6 +189,7 @@ nav:
189189
- examples/index.md
190190
- examples/first_app.md
191191
- examples/alternate_event_loops.md
192+
- examples/examples.md
192193
- Plugins:
193194
- plugins/index.md
194195
- plugins/external_test.md
@@ -219,4 +220,4 @@ extra_css:
219220

220221
# Include extra JS to setup Read the Docs addons integrations
221222
extra_javascript:
222-
- javascripts/readthedocs.js
223+
- javascripts/readthedocs.js

0 commit comments

Comments
 (0)