I'm writing a little CLI in Python (as an extension to Mercurial) and would like to support tab-completion. Specifically, I would like catch tabs in the prompt and show a list of matching options (just like bash).
Example: Enter section name:
ext*TAB*
extensions
extras
The problem is I'm not sure how to catch the Tab events. I'm using the ui.prompt()
API of Mercurial, which is just calling raw_input()
under the hood.
As far as I know, raw_input()
only returns on 'enter' and if a user enters a tab, the string returned simply includes a "\t"
.
For that you use the readline
module.
Simplest code I can think:
import readline
COMMANDS = ['extra', 'extension', 'stuff', 'errors',
'email', 'foobar', 'foo']
def complete(text, state):
for cmd in COMMANDS:
if cmd.startswith(text):
if not state:
return cmd
else:
state -= 1
readline.parse_and_bind("tab: complete")
readline.set_completer(complete)
raw_input('Enter section name: ')
Example usage:
Enter section name: <tab>
email errors extension extra foo foobar stuff
Enter section name: e<tab>
email errors extension extra
Enter section name: ext<tab>
extension extra
Besides completion, readline
provides you with: