Browse Source

Added aria2c bash_completion.

make_bash_completion.py generates aria2c bash_completion using `aria2c
--help=#all'.
Tatsuhiro Tsujikawa 15 years ago
parent
commit
8f39257fd5

+ 3 - 0
doc/Makefile.am

@@ -5,6 +5,9 @@ doc_xmlrpcdir = $(docdir)/xmlrpc
 dist_doc_xmlrpc_DATA = xmlrpc/aria2mon \
 	xmlrpc/aria2rpc \
 	xmlrpc/README.txt
+doc_bashcompletiondir = $(docdir)/bash_completion
+dist_doc_bashcompletion_DATA = bash_completion/README.txt \
+	bash_completion/aria2c
 
 if HAVE_A2X
 aria2c.1: aria2c.1.asciidoc

+ 11 - 0
doc/bash_completion/README.txt

@@ -0,0 +1,11 @@
+Bash_completion for aria2c
+==========================
+
+Install
+-------
+
+Copy 'aria2c' to the directory where bash_completion searches
+completion files.  For Debian and Ubuntu, copy 'aria2c' to
+'/etc/bash_completion.d/' and run
+
+. /etc/bash_completion

File diff suppressed because it is too large
+ 64 - 0
doc/bash_completion/aria2c


+ 162 - 0
doc/bash_completion/make_bash_completion.py

@@ -0,0 +1,162 @@
+#!/usr/bin/env python
+
+import subprocess
+from StringIO import StringIO
+import re
+import sys
+
+class Option:
+    def __init__(self, long_opt, short_opt, optional):
+        self.long_opt = long_opt
+        self.short_opt = short_opt
+        self.optional = optional
+        self.values = []
+
+def get_all_options(cmd):
+    opt_pattern = re.compile(r' (?:(-.), )?(--[^\s\[=]+)(\[)?')
+    values_pattern = re.compile(r'\s+Possible Values: (.+)')
+    proc = subprocess.Popen([cmd, "--help=#all"], stdout=subprocess.PIPE)
+    stdoutdata, stderrdata = proc.communicate()
+    cur_option = None
+    opts = {}
+    for line in StringIO(stdoutdata):
+        match = opt_pattern.match(line)
+        if match:
+            long_opt = match.group(2)
+            short_opt = match.group(1)
+            optional = match.group(3) == '['
+            if cur_option:
+                opts[cur_option.long_opt] = cur_option
+            cur_option = Option(long_opt, short_opt, optional)
+        else:
+            match = values_pattern.match(line)
+            if match:
+                cur_option.values = match.group(1).split(', ')
+    if cur_option:
+        opts[cur_option.long_opt] = cur_option
+
+    # for opt in opts.itervalues():
+    #     print opt.short_opt, opt.long_opt, opt.optional, opt.values
+
+    return opts
+
+def output_value_case(out, key, values):
+    out.write("""\
+        {0})
+            COMPREPLY=( $( compgen -W '{1}' -- "$cur" ) )
+            return 0
+            ;;
+""".format(key, " ".join(values)))
+
+def output_value_case_file_comp(out, key, exts):
+    out.write("""\
+        {0})
+            _filedir '@({1})'
+            return 0
+            ;;
+""".format(key, '|'.join(exts)))
+
+def output_value_case_dir_comp(out, key):
+    out.write("""\
+        {0})
+            _filedir -d
+            return 0
+            ;;
+""".format(key))
+
+def output_case(out, opts):
+    out.write("""\
+_aria2c()
+{
+    local cur prev split=false
+    COMPREPLY=()
+    COMP_WORDBREAKS=${COMP_WORDBREAKS//=}
+
+    cmd=${COMP_WORDS[0]}
+    _get_comp_words_by_ref cur prev
+""")
+    bool_opts = []
+    nonbool_opts = []
+    for opt in opts.itervalues():
+        if opt.values == ['true', 'false']:
+            bool_opts.append(opt)
+        else:
+            nonbool_opts.append(opt)
+
+    out.write("""\
+    case $prev in
+""")
+    # Complete pre-defined option arguments
+    for long_opt in ['--ftp-type',
+                     '--proxy-method',
+                     '--metalink-preferred-protocol',
+                     '--bt-min-crypto-level',
+                     '--follow-metalink',
+                     '--file-allocation',
+                     '--log-level',
+                     '--uri-selector',
+                     '--event-poll',
+                     '--follow-torrent']:
+        opt = opts[long_opt]
+        output_value_case(out, opt.long_opt, opt.values)
+    # Complete directory
+    dir_opts = []
+    for opt in opts.itervalues():
+        if opt.values and opt.values[0] == '/path/to/directory':
+            dir_opts.append(opt)
+    # Complete file
+    output_value_case_dir_comp(out,'|'.join([opt.long_opt for opt in dir_opts]))
+    # Complete specific file type
+    output_value_case_file_comp(out, '--torrent-file', ['torrent'])
+    output_value_case_file_comp(out, '--metalink-file', ['meta4', 'metalink'])
+    out.write("""\
+    esac
+""")
+    # Complete option name.
+    out.write("""\
+    case $cur in
+        -*)
+            COMPREPLY=( $( compgen -W '\
+""")
+    bool_values = [ 'true', 'false' ]
+    for opt in opts.itervalues():
+        out.write(opt.long_opt)
+        out.write(' ')
+        # Options which takes optional argument needs "=" between
+        # option name and value, so we complete them including "=" and
+        # value here.
+        if opt.optional:
+            if bool_values == opt.values:
+                # Because boolean option takes true when argument is
+                # omitted, we just complete additional 'false' option
+                # only.
+                out.write('='.join([opt.long_opt, 'false']))
+                out.write(' ')
+            else:
+                for value in opt.values:
+                    out.write('='.join([opt.long_opt, value]))
+                    out.write(' ')
+
+    out.write("""\
+' -- "$cur" ) )
+            ;;
+""")
+    # If no option found for completion then complete with files.
+    out.write("""\
+        *)
+            _filedir '@(torrent|meta4|metalink|text|txt|list|lst)'
+            [ ${#COMPREPLY[@]} -eq 0 ] && _filedir
+            return 0
+    esac
+    return 0
+}
+complete -F _aria2c aria2c
+""")
+
+if __name__ == '__main__':
+    if len(sys.argv) < 2:
+        print "Generates aria2c(1) bash_completion using `aria2c --help=#all'"
+        print "Usage: make_bash_completion.py /path/to/aria2c"
+        exit(1)
+    opts = get_all_options(sys.argv[1])
+    output_case(sys.stdout, opts)

Some files were not shown because too many files changed in this diff