Skip to content

Commit ae4e4bb

Browse files
authored
Update guide.md
1 parent 1296209 commit ae4e4bb

File tree

1 file changed

+35
-0
lines changed

1 file changed

+35
-0
lines changed

docs/guide.md

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,36 @@
1+
# 1. The way from [python-bugzilla](https://github.com/python-bugzilla/python-bugzilla)
12

3+
## 1.1 About *MI*
4+
5+
### 1.1.1 WHAT
6+
7+
**MI** stands for **Machine Interface**. The concept of MI originates from the well-known [GDB: The GNU Project Debugger](https://www.sourceware.org/gdb/) with docs at [GDB User Manual - The GDB/MI Interface](https://sourceware.org/gdb/current/onlinedocs/gdb/GDB_002fMI.html#GDB_002fMI).
8+
9+
For this project, when you run **MI** from your terminal, it starts to wait until it reads a line from `stdin`, then performs the corresponding operation, and finally writes some results and necessary information to `stdout`. Of course, these corresponding operations may also include reading some strings from `stdin`, such as obtaining the user name and password during interactive login.
10+
11+
### 1.1.2 WHY
12+
13+
[python-bugzilla](https://github.com/python-bugzilla/python-bugzilla) is undoubtedly an excellent project. It is packaged as a python library and published on [python-bugzilla - PyPI](https://pypi.org/project/python-bugzilla/). After running the installation scripts in `setup.py`, users could not only `import bugzilla` in their code, but also run `/usr/bin/bugzilla` directly in the terminal to use it through **CLI**.
14+
15+
However, through **CLI**, one call of `/usr/bin/bugzilla` can only complete one action, and each run requires some complex internal processes, such as detecting the basic information of the target, establishing HTTP(S) connections, etc. These expensive internal processes disappear from RAM with the end of script execution, and no cache mechanism is established on the disks.
16+
17+
Therefore, we consider deploying a loop-like structure and some cache mechanisms and in our new interface, so that multiple actions can be performed just in a single run, and shared information can be used repeatedly to reduce the overhead.
18+
19+
Not only that, we also hope that our new interface can **not only** be friendly to old users and provide compatibility as much as possible, **but also** provide machine-oriented convenience, so that it can be used as a backend of automatic control systems such as [expect](https://man7.org/linux/man-pages/man1/expect.1.html), [pexpect](https://github.com/pexpect/pexpect), [wexpect](https://github.com/raczben/wexpect), etc. (*This may remind you that running **python-bugzilla** in a separate process to avoid the infection of **GPL-2.0 license** to some extent. But this is surely NOT our original intention. We sincerely hope that you readers always be loyal to the spirit of open-source.*)
20+
21+
All the above reminds us of [GDB/MI Interface](https://sourceware.org/gdb/current/onlinedocs/gdb/GDB_002fMI.html#GDB_002fMI). So we borrowed the concept of **MI** from here and developed what you see today: run `bugzilla-mi`, after seeing the prompt of *ArgumentParser waiting*, type just exactly the same parameters to `stdin` when running `bugzilla-cli`, then press Enter (actually a **line break** is typed in), and then continue to type something or just wait, and finally get the expected output in `stdout`. After that you will continue to see the prompt of *ArgumentParser waiting*, and then get into another new round of typing parameters.
22+
23+
### 1.1.3 HOW
24+
25+
It is easy to find that after installation running `/usr/bin/bugzilla` in terminal is exactly equivalent to running `python ./bugzilla-cli` in the project root directory of [python-bugzilla](https://github.com/python-bugzilla/python-bugzilla). And `bugzilla-cli` is actually just a wrapper of `_cli.main`. So we do the surgery on a copy of `_cli.py`, i.e., `_mi.py`. Although original `_cli.py` looks complex, it is highly cohesive and low coupling, so the surgery is easy. We
26+
27+
* wrap a cluster of output messages (consisting of single or multiple lines) between *start-flag-line* `|v>*<v|` and *end-flag-line* `|^>*<^|`;
28+
* redirect logs output so that it is written to a file instead of being written to `stderr` to avoid potential impact;
29+
* patch built-in `argparse.ArgumentParser` to make it print message to `stdout` in our new format, and no longer call `sys.exit` when it fails in parsing;
30+
* patch other functions that have calls of `print` to make them print to `stdout` in our new format;
31+
* add a cache mechanism in `_make_bz_instance` to make a new instance when necessary;
32+
* add many `try-except` and `raise` statements to make the round by round loop process run robustly without unexpected interruption.
33+
34+
35+
36+
## 1.2 Something shrunk

0 commit comments

Comments
 (0)