code

파이썬, 명령 줄 프로그램을 인터프리터가 아닌 임의의 것을 자동 완성하는 방법

codestyles 2020. 9. 18. 08:14
반응형

파이썬, 명령 줄 프로그램을 인터프리터가 아닌 임의의 것을 자동 완성하는 방법


파이썬 인터프리터 (유닉스에서)에서 파이썬 객체의 자동 완성을 설정하는 방법을 알고 있습니다.

  • Google은이를 수행하는 방법에 대한 설명을 위해 많은 히트를 표시합니다.
  • 안타깝게도 참조가 너무 많아서 내가해야 할 일을 찾기가 어렵습니다. 약간 다릅니다.

파이썬으로 작성된 명령 줄 프로그램에서 임의 항목의 탭 / 자동 완성을 활성화하는 방법을 알아야합니다.

내 특정 사용 사례는 이메일을 보내야하는 명령 줄 Python 프로그램입니다. 사용자가 이메일 주소의 일부를 입력 할 때 (그리고 선택적으로 TAB 키를 누를 때) 이메일 주소 (디스크에 주소가 있음)를 자동 완성 할 수 있기를 원합니다.

Windows 나 Mac에서 작동하는 데 필요하지 않으며 Linux 만 있습니다.


Python의 readline바인딩을 사용합니다 . 예를 들면

import readline

def completer(text, state):
    options = [i for i in commands if i.startswith(text)]
    if state < len(options):
        return options[state]
    else:
        return None

readline.parse_and_bind("tab: complete")
readline.set_completer(completer)

공식 모듈 문서 는 그다지 상세하지 않습니다. 자세한 내용은 readline 문서 를 참조하세요.


을 따르지 cmd를 문서를 그리고 당신은 괜찮을거야

import cmd

addresses = [
    'here@blubb.com',
    'foo@bar.com',
    'whatever@wherever.org',
]

class MyCmd(cmd.Cmd):
    def do_send(self, line):
        pass

    def complete_send(self, text, line, start_index, end_index):
        if text:
            return [
                address for address in addresses
                if address.startswith(text)
            ]
        else:
            return addresses


if __name__ == '__main__':
    my_cmd = MyCmd()
    my_cmd.cmdloop()

탭 출력-> 탭-> 보내기-> 탭-> 탭-> f-> 탭

(Cmd)
help  send
(Cmd) send
foo@bar.com            here@blubb.com         whatever@wherever.org
(Cmd) send foo@bar.com
(Cmd)

귀하의 질문에 "NOT 인터프리터"라고 말했기 때문에 파이썬 readline 등과 관련된 답변을 원하지 않는 것 같습니다. ( 편집 : 돌이켜 보면 분명히 그렇지 않습니다. Ho hum. 어쨌든이 정보가 흥미 롭다고 생각하므로 여기에 남겨 두겠습니다. )

나는 당신 이 이것 이후에있을 것이라고 생각합니다 .

임의의 명령에 셸 수준 완성을 추가하여 bash의 자체 탭 완성을 확장하는 것입니다.

In a nutshell, you'll create a file containing a shell-function that will generate possible completions, save it into /etc/bash_completion.d/ and register it with the command complete. Here's a snippet from the linked page:

_foo() 
{
    local cur prev opts
    COMPREPLY=()
    cur="${COMP_WORDS[COMP_CWORD]}"
    prev="${COMP_WORDS[COMP_CWORD-1]}"
    opts="--help --verbose --version"

    if [[ ${cur} == -* ]] ; then
        COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) )
        return 0
    fi
}
complete -F _foo foo

In this case, the typing foo --[TAB] will give you the values in the variable opts, i.e. --help, --verbose and --version. For your purposes, you'll essentially want to customise the values that are put into opts.

Do have a look at the example on the linked page, it's all pretty straightforward.


I am surprised that nobody has mentioned argcomplete, here is an example from the docs:

from argcomplete.completers import ChoicesCompleter

parser.add_argument("--protocol", choices=('http', 'https', 'ssh', 'rsync', 'wss'))
parser.add_argument("--proto").completer=ChoicesCompleter(('http', 'https', 'ssh', 'rsync', 'wss'))

Here is a full-working version of the code that was very supplied by ephemient here (thank you).

import readline

addrs = ['angela@domain.com', 'michael@domain.com', 'david@test.com']

def completer(text, state):
    options = [x for x in addrs if x.startswith(text)]
    try:
        return options[state]
    except IndexError:
        return None

readline.set_completer(completer)
readline.parse_and_bind("tab: complete")

while 1:
    a = raw_input("> ")
    print "You entered", a

# ~/.pythonrc
import rlcompleter, readline
readline.parse_and_bind('tab:complete')

# ~/.bashrc
export PYTHONSTARTUP=~/.pythonrc

You can try using the Python Prompt Toolkit, a library for building interactive command line applications in Python.

The library makes it easy to add interactive autocomplete functionality, allowing the user to use the Tab key to visually cycle through the available choices. The library is cross-platform (Linux, OS X, FreeBSD, OpenBSD, Windows). Example:

pgcli - Python Prompt Toolkit

(Image source: pcgli)


The posted answers work fine but I have open sourced an autocomplete library that I wrote at work. We have been using it for a while in production and it is fast, stable and easy to use. It even has a demo mode so you can quickly test what you would get as you type words.

To install it, simply run: pip install fast-autocomplete

Here is an example:

>>> from fast_autocomplete import AutoComplete
>>> words = {'book': {}, 'burrito': {}, 'pizza': {}, 'pasta':{}}
>>> autocomplete = AutoComplete(words=words)
>>> autocomplete.search(word='b', max_cost=3, size=3)
[['book'], ['burrito']]
>>> autocomplete.search(word='bu', max_cost=3, size=3)
[['burrito']]
>>> autocomplete.search(word='barrito', max_cost=3, size=3)  # mis-spelling
[['burrito']]

Checkout: https://github.com/wearefair/fast-autocomplete for the source code.

And here is an explanation of how it works: http://zepworks.com/posts/you-autocomplete-me/

It deals with mis-spellings and optionally sorting by the weight of the word. (let's say burrito is more important than book, then you give burrito a higher "count" and it will show up first before book in the results.

Words is a dictionary and each word can have a context. For example the "count", how to display the word, some other context around the word etc. In this example words didn't have any context.

참고URL : https://stackoverflow.com/questions/187621/how-to-make-a-python-command-line-program-autocomplete-arbitrary-things-not-int

반응형