Fix for x86_64 build fail
[platform/upstream/connectedhomeip.git] / third_party / pigweed / repo / pw_cli / docs.rst
1 .. _module-pw_cli:
2
3 ------
4 pw_cli
5 ------
6 This directory contains the ``pw`` command line interface (CLI) that facilitates
7 working with Pigweed. The CLI module adds several subcommands prefixed with
8 ``pw``, and provides a mechanism for other Pigweed modules to behave as
9 "plugins" and register themselves as ``pw`` commands as well. After activating
10 the Pigweed environment, these commands will be available for use.
11
12 ``pw`` includes the following commands by default:
13
14 .. code-block:: text
15
16   doctor        Check that the environment is set up correctly for Pigweed.
17   format        Check and fix formatting for source files.
18   help          Display detailed information about pw commands.
19   logdemo       Show how logs look at various levels.
20   module-check  Check that a module matches Pigweed's module guidelines.
21   test          Run Pigweed unit tests built using GN.
22   watch         Watch files for changes and rebuild.
23
24 To see an up-to-date list of ``pw`` subcommands, run ``pw --help``.
25
26 Invoking  ``pw``
27 ================
28 ``pw`` subcommands are invoked by providing the command name. Arguments prior to
29 the command are interpreted by ``pw`` itself; all arguments after the command
30 name are interpreted by the command.
31
32 Here are some example invocations of ``pw``:
33
34 .. code-block:: text
35
36   # Run the doctor command
37   $ pw doctor
38
39   # Run format --fix with debug-level logs
40   $ pw --loglevel debug format --fix
41
42   # Display help for the pw command
43   $ pw -h watch
44
45   # Display help for the watch command
46   $ pw watch -h
47
48 Registering ``pw`` plugins
49 ==========================
50 Projects can register their own Python scripts as ``pw`` commands. ``pw``
51 plugins are registered by providing the command name, module, and function in a
52 ``PW_PLUGINS`` file. ``PW_PLUGINS`` files can add new commands or override
53 built-in commands. Since they are accessed by module name, plugins must be
54 defined in Python packages that are installed in the Pigweed virtual
55 environment.
56
57 Plugin registrations in a ``PW_PLUGINS`` file apply to the their directory and
58 all subdirectories, similarly to configuration files like ``.clang-format``.
59 Registered plugins appear as commands in the ``pw`` tool when ``pw`` is run from
60 those directories.
61
62 Projects that wish to register commands might place a ``PW_PLUGINS`` file in the
63 root of their repo. Multiple ``PW_PLUGINS`` files may be applied, but the ``pw``
64 tool gives precedence to a ``PW_PLUGINS`` file in the current working directory
65 or the nearest parent directory.
66
67 PW_PLUGINS file format
68 ----------------------
69 ``PW_PLUGINS`` contains one plugin entry per line in the following format:
70
71 .. code-block:: python
72
73   # Lines that start with a # are ignored.
74   <command name> <Python module> <function>
75
76 The following example registers three commands:
77
78 .. code-block:: python
79
80   # Register the presubmit script as pw presubmit
81   presubmit my_cool_project.tools run_presubmit
82
83   # Override the pw test command with a custom version
84   test my_cool_project.testing run_test
85
86   # Add a custom command
87   flash my_cool_project.flash main
88
89 Defining a plugin function
90 --------------------------
91 Any function without required arguments may be used as a plugin function. The
92 function should return an int, which the ``pw`` uses as the exit code. The
93 ``pw`` tool uses the function docstring as the help string for the command.
94
95 Typically, ``pw`` commands parse their arguments with the ``argparse`` module.
96 ``pw`` sets ``sys.argv`` so it contains only the arguments for the plugin,
97 so plugins can behave the same whether they are executed independently or
98 through ``pw``.
99
100 Example
101 ^^^^^^^
102 This example shows a function that is registered as a ``pw`` plugin.
103
104 .. code-block:: python
105
106   # my_package/my_module.py
107
108   def _do_something(device):
109       ...
110
111   def main() -> int:
112       """Do something to a connected device."""
113
114       parser = argparse.ArgumentParser(description=__doc__)
115       parser.add_argument('--device', help='Set which device to target')
116       return _do_something(**vars(parser.parse_args()))
117
118
119   if __name__ == '__main__':
120       logging.basicConfig(format='%(message)s', level=logging.INFO)
121       sys.exit(main())
122
123 This plugin is registered in a ``PW_PLUGINS`` file in the current working
124 directory or a parent of it.
125
126 .. code-block:: python
127
128   # Register my_commmand
129   my_command my_package.my_module main
130
131 The function is now available through the ``pw`` command, and will be listed in
132 ``pw``'s help. Arguments after the command name are passed to the plugin.
133
134 .. code-block:: text
135
136   $ pw
137
138    ▒█████▄   █▓  ▄███▒  ▒█    ▒█ ░▓████▒ ░▓████▒ ▒▓████▄
139     ▒█░  █░ ░█▒ ██▒ ▀█▒ ▒█░ █ ▒█  ▒█   ▀  ▒█   ▀  ▒█  ▀█▌
140     ▒█▄▄▄█░ ░█▒ █▓░ ▄▄░ ▒█░ █ ▒█  ▒███    ▒███    ░█   █▌
141     ▒█▀     ░█░ ▓█   █▓ ░█░ █ ▒█  ▒█   ▄  ▒█   ▄  ░█  ▄█▌
142     ▒█      ░█░ ░▓███▀   ▒█▓▀▓█░ ░▓████▒ ░▓████▒ ▒▓████▀
143
144   usage: pw [-h] [-C DIRECTORY] [-l LOGLEVEL] [--no-banner] [command] ...
145
146   The Pigweed command line interface (CLI).
147
148   ...
149
150   supported commands:
151     doctor        Check that the environment is set up correctly for Pigweed.
152     format        Check and fix formatting for source files.
153     help          Display detailed information about pw commands.
154     ...
155     my_command    Do something to a connected device.
156
157   $ pw my_command -h
158
159    ▒█████▄   █▓  ▄███▒  ▒█    ▒█ ░▓████▒ ░▓████▒ ▒▓████▄
160     ▒█░  █░ ░█▒ ██▒ ▀█▒ ▒█░ █ ▒█  ▒█   ▀  ▒█   ▀  ▒█  ▀█▌
161     ▒█▄▄▄█░ ░█▒ █▓░ ▄▄░ ▒█░ █ ▒█  ▒███    ▒███    ░█   █▌
162     ▒█▀     ░█░ ▓█   █▓ ░█░ █ ▒█  ▒█   ▄  ▒█   ▄  ░█  ▄█▌
163     ▒█      ░█░ ░▓███▀   ▒█▓▀▓█░ ░▓████▒ ░▓████▒ ▒▓████▀
164
165   usage: pw my_command [-h] [--device DEVICE]
166
167   Do something to a connected device.
168
169   optional arguments:
170     -h, --help       show this help message and exit
171     --device DEVICE  Set which device to target
172
173 Branding Pigweed's tooling
174 ==========================
175 An important part of starting a new project is picking a name, and in the case
176 of Pigweed, designing a banner for the project. Pigweed supports configuring
177 the banners by setting environment variables:
178
179 * ``PW_BRANDING_BANNER`` - Absolute path to a filename containing a banner to
180   display when running the ``pw`` commands. See the example below.
181 * ``PW_BRANDING_BANNER_COLOR`` - Color of the banner. Possible values include:
182   ``red``, ``bold_red``, ``yellow``, ``bold_yellow``, ``green``,
183   ``bold_green``, ``blue``, ``cyan``, ``magenta``, ``bold_white``,
184   ``black_on_white``. See ``pw_cli.colors`` for details.
185
186 The below example shows how to manually change the branding at the command
187 line. However, these environment variables should be set in the project root's
188 ``bootstrap.sh`` before delegating to Pigweed's upstream ``bootstrap.sh``.
189
190 .. code-block:: text
191
192   $ cat foo-banner.txt
193
194    ▒██████  ░▓██▓░  ░▓██▓░
195     ▒█░    ▒█   ▒█ ▒█   ▒█
196     ▒█▄▄▄▄ ▒█ █ ▒█ ▒█ █ ▒█
197     ▒█▀    ▒█   ▒█ ▒█   ▒█
198     ▒█      ░▓██▓░  ░▓██▓░
199
200   $ export PW_BRANDING_BANNER="$(pwd)/foo-banner.txt"
201   $ export PW_BRANDING_BANNER_COLOR="bold_red"
202   $ pw logdemo
203
204    ▒██████  ░▓██▓░  ░▓██▓░
205     ▒█░    ▒█   ▒█ ▒█   ▒█
206     ▒█▄▄▄▄ ▒█ █ ▒█ ▒█ █ ▒█
207     ▒█▀    ▒█   ▒█ ▒█   ▒█
208     ▒█      ░▓██▓░  ░▓██▓░
209
210   20200610 12:03:44 CRT This is a critical message
211   20200610 12:03:44 ERR There was an error on our last operation
212   20200610 12:03:44 WRN Looks like something is amiss; consider investigating
213   20200610 12:03:44 INF The operation went as expected
214   20200610 12:03:44 OUT Standard output of subprocess
215
216 The branding is not purely visual; it serves to make it clear which project an
217 engineer is working with.
218
219 Making the ASCII / ANSI art
220 ---------------------------
221 The most direct way to make the ASCII art is to create it with a text editor.
222 However, there are some tools to make the process faster and easier.
223
224 * `Patorjk's ASCII art generator <http://patorjk.com/software/taag/>`_ - A
225   great starting place, since you can copy and paste straight from the browser
226   into a file, and then point ``PW_BRANDING_BANNER`` at it.  Most of the fonts
227   use normal ASCII characters; and fonts with extended ASCII characters use the
228   Unicode versions of them (needed for modern terminals).
229 * `Online ANSII Edit by Andy Herbert
230   <http://andyherbert.github.io/ansiedit/public/index.html>`_ - Browser based
231   editor that can export to mixed UTF-8 and ANSII color. It's also `open source
232   <https://github.com/andyherbert/ansiedit>`_. What's nice about this editor is
233   that you can create a multi-color banner, and save it with the ``File`` -->
234   ``Export as ANSi (UTF-8)`` option, and use it directly as a Pigweed banner.
235   One caveat is that the editor uses UTF-8 box drawing characters, which don't
236   work well with all terminals. However, the box drawing characters look so
237   slick on terminals that support them that we feel this is a worthwhile
238   tradeoff.
239
240 There are other options, but these require additional work to put into Pigweed
241 since they only export in the traditional ANS or ICE formats. The old ANS
242 formats do not have a converter (contributions welcome!). Here are some of the
243 options as of mid-2020:
244
245 * `Playscii <http://vectorpoem.com/playscii/>`_ - Actively maintained.
246 * `Moebius <https://github.com/blocktronics/moebius>`_ - Actively maintained.
247 * `SyncDraw <http://syncdraw.bbsdev.net/>`_ - Actively maintained, in 2020, in
248   a CVS repository.
249 * `PabloDraw <http://picoe.ca/products/pablodraw/>`_ - Works on most desktop
250   machines thanks to being written in .NET. Not maintained, but works well. Has
251   an impresive brush system for organic style drawing.
252 * `TheDraw <https://en.wikipedia.org/wiki/TheDraw>`_ - One of the most popular
253   ANSI art editors back in the 90s. Requires DOSBox to run on modern machines,
254   but otherwise works. It has some of the most impressive capabilities,
255   including supporting full-color multi-character fonts.
256
257 Future branding improvements
258 ----------------------------
259 Branding the ``pw`` tool is a great start, but more changes are planned:
260
261 - Supporting branding the ``bootstrap/activate`` banner, which for technical
262   reasons is not the same code as the banner printing from the Python tooling.
263   These will use the same ``PW_BRANDING_BANNER`` and
264   ``PW_BRANDING_BANNER_COLOR`` environment variables.
265 - Supporting renaming the ``pw`` command to something project specific, like
266   ``foo`` in this case.
267 - Re-coloring the log headers from the ``pw`` tool.