Skip to content

Commit f3c07a0

Browse files
authored
Merge pull request #614 from python-cmd2/help_text_script
Help text script
2 parents f593588 + 9946115 commit f3c07a0

File tree

3 files changed

+94
-1
lines changed

3 files changed

+94
-1
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
## 0.9.7 (TBD, 2018)
22
* Bug Fixes
33
* Fixed bug when user chooses a zero or negative index when calling ``Cmd.select()``
4+
* Restored behavior where ``cmd_echo`` always starts as False in a py script. This was broken in 0.9.5.
45
* Enhancements
56
* **cmdloop** now only attempts to register a custom signal handler for SIGINT if running in the main thread
67
* commands run as a result of ``default_to_shell`` being **True** now run via ``do_shell()`` and are saved

cmd2/cmd2.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2968,6 +2968,10 @@ def run(filename: str):
29682968
:param filename: filename of *.py script file to run
29692969
"""
29702970
expanded_filename = os.path.expanduser(filename)
2971+
2972+
# cmd_echo defaults to False for scripts. The user can always toggle this value in their script.
2973+
bridge.cmd_echo = False
2974+
29712975
try:
29722976
with open(expanded_filename) as f:
29732977
interp.runcode(f.read())
@@ -2989,12 +2993,14 @@ def run(filename: str):
29892993
interp = InteractiveConsole(locals=localvars)
29902994
interp.runcode('import sys, os;sys.path.insert(0, os.getcwd())')
29912995

2996+
# Check if the user is running a Python statement on the command line
29922997
if args.command:
29932998
full_command = args.command
29942999
if args.remainder:
29953000
full_command += ' ' + ' '.join(args.remainder)
29963001

2997-
# If running at the CLI, print the output of the command
3002+
# Set cmd_echo to True so PyscriptBridge statements like: py app('help')
3003+
# run at the command line will print their output.
29983004
bridge.cmd_echo = True
29993005
interp.runcode(full_command)
30003006

examples/scripts/save_help_text.py

Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
# coding=utf-8
2+
# flake8: noqa F821
3+
"""
4+
A cmd2 script that saves the help text for every command and sub-command to a file.
5+
This is meant to be run within a cmd2 session using pyscript.
6+
"""
7+
8+
import argparse
9+
import os
10+
import sys
11+
from typing import List, TextIO
12+
13+
ASTERISKS = "********************************************************"
14+
15+
16+
def get_sub_commands(parser: argparse.ArgumentParser) -> List[str]:
17+
"""Get a list of sub-commands for an ArgumentParser"""
18+
sub_cmds = []
19+
20+
# Check if this is parser has sub-commands
21+
if parser is not None and parser._subparsers is not None:
22+
23+
# Find the _SubParsersAction for the sub-commands of this parser
24+
for action in parser._subparsers._actions:
25+
if isinstance(action, argparse._SubParsersAction):
26+
for sub_cmd, sub_cmd_parser in action.choices.items():
27+
sub_cmds.append(sub_cmd)
28+
29+
# Look for nested sub-commands
30+
for nested_sub_cmd in get_sub_commands(sub_cmd_parser):
31+
sub_cmds.append('{} {}'.format(sub_cmd, nested_sub_cmd))
32+
33+
break
34+
35+
sub_cmds.sort()
36+
return sub_cmds
37+
38+
39+
def add_help_to_file(command: str, outfile: TextIO) -> None:
40+
"""Write a header and help text for a command to the output file"""
41+
header = '{}\nCOMMAND: {}\n{}\n'.format(ASTERISKS, command, ASTERISKS)
42+
outfile.write(header)
43+
44+
result = app('help {}'.format(command))
45+
outfile.write(result.stdout)
46+
47+
48+
def main() -> None:
49+
"""Main function of this script"""
50+
51+
# Make sure we have access to self
52+
if 'self' not in globals():
53+
print("Run 'set locals_in_py true' and then rerun this script")
54+
return
55+
56+
# Make sure the user passed in an output file
57+
if len(sys.argv) != 2:
58+
print("Usage: {} <output_file>".format(os.path.basename(sys.argv[0])))
59+
return
60+
61+
# Open the output file
62+
outfile_path = os.path.expanduser(sys.argv[1])
63+
try:
64+
outfile = open(outfile_path, 'w')
65+
except OSError as e:
66+
print("Error opening {} because: {}".format(outfile_path, e))
67+
return
68+
69+
# Get a list of all commands and help topics and then filter out duplicates
70+
to_save = list(set(self.get_all_commands()) | set(self.get_help_topics()))
71+
to_save.sort()
72+
73+
for item in to_save:
74+
add_help_to_file(item, outfile)
75+
76+
# Add any sub-commands
77+
for subcmd in get_sub_commands(getattr(self.cmd_func(item), 'argparser', None)):
78+
full_cmd = '{} {}'.format(item, subcmd)
79+
add_help_to_file(full_cmd, outfile)
80+
81+
outfile.close()
82+
print("Output written to {}".format(outfile_path))
83+
84+
85+
# Run main function
86+
main()

0 commit comments

Comments
 (0)