diff --git a/CHANGES b/CHANGES index 5639ea4..c76edbb 100644 --- a/CHANGES +++ b/CHANGES @@ -3,6 +3,31 @@ Click Changelog This contains all major version changes between Click releases. +Version 6.6 +----------- + +(bugfix release; released on April 4th 2016) + +- Fix bug in `click.Path` where it would crash when passed a `-`. See #551. + +Version 6.4 +----------- + +(bugfix release; released on March 24th 2016) + +- Fix bug in bash completion where click would discard one or more trailing + arguments. See #471. + +Version 6.3 +----------- + +(bugfix release; released on February 22 2016) + +- Fix argument checks for interpreter invoke with `-m` and `-c` + on Windows. +- Fixed a bug that cased locale detection to error out on Python 3. + + Version 6.2 ----------- diff --git a/PKG-INFO b/PKG-INFO index cd4688c..d569270 100644 --- a/PKG-INFO +++ b/PKG-INFO @@ -1,6 +1,6 @@ Metadata-Version: 1.1 Name: click -Version: 6.2 +Version: 6.6 Summary: A simple wrapper around optparse for powerful command line utilities. Home-page: http://github.com/mitsuhiko/click Author: Armin Ronacher diff --git a/artwork/.DS_Store b/artwork/.DS_Store deleted file mode 100644 index cd88301..0000000 Binary files a/artwork/.DS_Store and /dev/null differ diff --git a/click.egg-info/PKG-INFO b/click.egg-info/PKG-INFO index cd4688c..d569270 100644 --- a/click.egg-info/PKG-INFO +++ b/click.egg-info/PKG-INFO @@ -1,6 +1,6 @@ Metadata-Version: 1.1 Name: click -Version: 6.2 +Version: 6.6 Summary: A simple wrapper around optparse for powerful command line utilities. Home-page: http://github.com/mitsuhiko/click Author: Armin Ronacher diff --git a/click.egg-info/SOURCES.txt b/click.egg-info/SOURCES.txt index 19999ad..e524cba 100644 --- a/click.egg-info/SOURCES.txt +++ b/click.egg-info/SOURCES.txt @@ -5,7 +5,6 @@ Makefile README setup.cfg setup.py -artwork/.DS_Store artwork/logo.svg click/__init__.py click/_bashcomplete.py @@ -61,7 +60,6 @@ docs/_static/click.png docs/_static/click@2x.png docs/_templates/sidebarintro.html docs/_templates/sidebarlogo.html -examples/.DS_Store examples/README examples/aliases/README examples/aliases/aliases.ini @@ -77,55 +75,42 @@ examples/complex/complex/cli.py examples/complex/complex/commands/__init__.py examples/complex/complex/commands/cmd_init.py examples/complex/complex/commands/cmd_status.py -examples/demo/demo.py -examples/imagepipe/.DS_Store examples/imagepipe/.gitignore examples/imagepipe/README examples/imagepipe/example01.jpg examples/imagepipe/example02.jpg examples/imagepipe/imagepipe.py examples/imagepipe/setup.py -examples/imagepipe/click_example_imagepipe.egg-info/PKG-INFO -examples/imagepipe/click_example_imagepipe.egg-info/SOURCES.txt -examples/imagepipe/click_example_imagepipe.egg-info/dependency_links.txt -examples/imagepipe/click_example_imagepipe.egg-info/entry_points.txt -examples/imagepipe/click_example_imagepipe.egg-info/requires.txt -examples/imagepipe/click_example_imagepipe.egg-info/top_level.txt examples/inout/README examples/inout/inout.py examples/inout/setup.py examples/naval/README examples/naval/naval.py examples/naval/setup.py -examples/naval/click_example_naval.egg-info/PKG-INFO -examples/naval/click_example_naval.egg-info/SOURCES.txt -examples/naval/click_example_naval.egg-info/dependency_links.txt -examples/naval/click_example_naval.egg-info/entry_points.txt -examples/naval/click_example_naval.egg-info/requires.txt -examples/naval/click_example_naval.egg-info/top_level.txt +examples/plugins/BrokenPlugin/printer_bold.egg-info/PKG-INFO +examples/plugins/BrokenPlugin/printer_bold.egg-info/SOURCES.txt +examples/plugins/BrokenPlugin/printer_bold.egg-info/dependency_links.txt +examples/plugins/BrokenPlugin/printer_bold.egg-info/entry_points.txt +examples/plugins/BrokenPlugin/printer_bold.egg-info/top_level.txt +examples/plugins/printer.egg-info/PKG-INFO +examples/plugins/printer.egg-info/SOURCES.txt +examples/plugins/printer.egg-info/dependency_links.txt +examples/plugins/printer.egg-info/entry_points.txt +examples/plugins/printer.egg-info/top_level.txt examples/repo/README examples/repo/repo.py examples/repo/setup.py -examples/repo/click_example_repo.egg-info/PKG-INFO -examples/repo/click_example_repo.egg-info/SOURCES.txt -examples/repo/click_example_repo.egg-info/dependency_links.txt -examples/repo/click_example_repo.egg-info/entry_points.txt -examples/repo/click_example_repo.egg-info/requires.txt -examples/repo/click_example_repo.egg-info/top_level.txt examples/termui/README examples/termui/setup.py examples/termui/termui.py -examples/termui/click_example_termui.egg-info/PKG-INFO -examples/termui/click_example_termui.egg-info/SOURCES.txt -examples/termui/click_example_termui.egg-info/dependency_links.txt -examples/termui/click_example_termui.egg-info/entry_points.txt -examples/termui/click_example_termui.egg-info/requires.txt -examples/termui/click_example_termui.egg-info/top_level.txt +examples/termui/build/lib/termui.py +examples/termui/dist/click_example_termui-1.0-py3.4.egg examples/validation/README examples/validation/setup.py examples/validation/validation.py tests/conftest.py tests/test_arguments.py +tests/test_bashcomplete.py tests/test_basic.py tests/test_chain.py tests/test_commands.py diff --git a/click/__init__.py b/click/__init__.py index 07c21dc..3a7e3ee 100644 --- a/click/__init__.py +++ b/click/__init__.py @@ -95,4 +95,4 @@ __all__ = [ disable_unicode_literals_warning = False -__version__ = '6.2' +__version__ = '6.6' diff --git a/click/_bashcomplete.py b/click/_bashcomplete.py index 43feffb..d97b66a 100644 --- a/click/_bashcomplete.py +++ b/click/_bashcomplete.py @@ -30,27 +30,19 @@ def get_completion_script(prog_name, complete_var): def resolve_ctx(cli, prog_name, args): ctx = cli.make_context(prog_name, args, resilient_parsing=True) - while ctx.args and isinstance(ctx.command, MultiCommand): - cmd = ctx.command.get_command(ctx, ctx.args[0]) + while ctx.args + ctx.protected_args and isinstance(ctx.command, MultiCommand): + a = ctx.args + ctx.protected_args + cmd = ctx.command.get_command(ctx, a[0]) if cmd is None: return None - ctx = cmd.make_context(ctx.args[0], ctx.args[1:], parent=ctx, - resilient_parsing=True) + ctx = cmd.make_context(a[0], a[1:], parent=ctx, resilient_parsing=True) return ctx -def do_complete(cli, prog_name): - cwords = split_arg_string(os.environ['COMP_WORDS']) - cword = int(os.environ['COMP_CWORD']) - args = cwords[1:cword] - try: - incomplete = cwords[cword] - except IndexError: - incomplete = '' - +def get_choices(cli, prog_name, args, incomplete): ctx = resolve_ctx(cli, prog_name, args) if ctx is None: - return True + return choices = [] if incomplete and not incomplete[:1].isalnum(): @@ -64,7 +56,20 @@ def do_complete(cli, prog_name): for item in choices: if item.startswith(incomplete): - echo(item) + yield item + + +def do_complete(cli, prog_name): + cwords = split_arg_string(os.environ['COMP_WORDS']) + cword = int(os.environ['COMP_CWORD']) + args = cwords[1:cword] + try: + incomplete = cwords[cword] + except IndexError: + incomplete = '' + + for item in get_choices(cli, prog_name, args, incomplete): + echo(item) return True diff --git a/click/_unicodefun.py b/click/_unicodefun.py index c0c52aa..24b7031 100644 --- a/click/_unicodefun.py +++ b/click/_unicodefun.py @@ -64,6 +64,11 @@ def _verify_python3_env(): stderr=subprocess.PIPE).communicate()[0] good_locales = set() has_c_utf8 = False + + # Make sure we're operating on text here. + if isinstance(rv, bytes): + rv = rv.decode('ascii', 'replace') + for line in rv.splitlines(): locale = line.strip() if locale.lower().endswith(('.utf-8', '.utf8')): diff --git a/click/_winconsole.py b/click/_winconsole.py index f6cece4..9aed942 100644 --- a/click/_winconsole.py +++ b/click/_winconsole.py @@ -16,16 +16,19 @@ import time import ctypes import msvcrt from click._compat import _NonClosingTextIOWrapper, text_type, PY2 -from ctypes import byref, POINTER, pythonapi, c_int, c_char, c_char_p, \ +from ctypes import byref, POINTER, c_int, c_char, c_char_p, \ c_void_p, py_object, c_ssize_t, c_ulong, windll, WINFUNCTYPE +try: + from ctypes import pythonapi + PyObject_GetBuffer = pythonapi.PyObject_GetBuffer + PyBuffer_Release = pythonapi.PyBuffer_Release +except ImportError: + pythonapi = None from ctypes.wintypes import LPWSTR, LPCWSTR c_ssize_p = POINTER(c_ssize_t) -PyObject_GetBuffer = pythonapi.PyObject_GetBuffer -PyBuffer_Release = pythonapi.PyBuffer_Release - kernel32 = windll.kernel32 GetStdHandle = kernel32.GetStdHandle ReadConsoleW = kernel32.ReadConsoleW @@ -77,15 +80,20 @@ class Py_buffer(ctypes.Structure): _fields_.insert(-1, ('smalltable', c_ssize_t * 2)) -def get_buffer(obj, writable=False): - buf = Py_buffer() - flags = PyBUF_WRITABLE if writable else PyBUF_SIMPLE - PyObject_GetBuffer(py_object(obj), byref(buf), flags) - try: - buffer_type = c_char * buf.len - return buffer_type.from_address(buf.buf) - finally: - PyBuffer_Release(byref(buf)) +# On PyPy we cannot get buffers so our ability to operate here is +# serverly limited. +if pythonapi is None: + get_buffer = None +else: + def get_buffer(obj, writable=False): + buf = Py_buffer() + flags = PyBUF_WRITABLE if writable else PyBUF_SIMPLE + PyObject_GetBuffer(py_object(obj), byref(buf), flags) + try: + buffer_type = c_char * buf.len + return buffer_type.from_address(buf.buf) + finally: + PyBuffer_Release(byref(buf)) class _WindowsConsoleRawIOBase(io.RawIOBase): @@ -232,7 +240,7 @@ if PY2: if not arg.startswith('-') or arg == '-': break argv = argv[1:] - if arg in ('-c', '-m'): + if arg.startswith(('-c', '-m')): break return argv[1:] @@ -246,7 +254,8 @@ _stream_factories = { def _get_windows_console_stream(f, encoding, errors): - if encoding in ('utf-16-le', None) \ + if get_buffer is not None and \ + encoding in ('utf-16-le', None) \ and errors in ('strict', None) and \ hasattr(f, 'isatty') and f.isatty(): func = _stream_factories.get(f.fileno()) diff --git a/click/types.py b/click/types.py index 7a24747..3639002 100644 --- a/click/types.py +++ b/click/types.py @@ -418,26 +418,26 @@ class Path(ParamType): filename_to_ui(value) ), param, ctx) - if not self.file_okay and stat.S_ISREG(st.st_mode): - self.fail('%s "%s" is a file.' % ( - self.path_type, - filename_to_ui(value) - ), param, ctx) - if not self.dir_okay and stat.S_ISDIR(st.st_mode): - self.fail('%s "%s" is a directory.' % ( - self.path_type, - filename_to_ui(value) - ), param, ctx) - if self.writable and not os.access(value, os.W_OK): - self.fail('%s "%s" is not writable.' % ( - self.path_type, - filename_to_ui(value) - ), param, ctx) - if self.readable and not os.access(value, os.R_OK): - self.fail('%s "%s" is not readable.' % ( - self.path_type, - filename_to_ui(value) - ), param, ctx) + if not self.file_okay and stat.S_ISREG(st.st_mode): + self.fail('%s "%s" is a file.' % ( + self.path_type, + filename_to_ui(value) + ), param, ctx) + if not self.dir_okay and stat.S_ISDIR(st.st_mode): + self.fail('%s "%s" is a directory.' % ( + self.path_type, + filename_to_ui(value) + ), param, ctx) + if self.writable and not os.access(value, os.W_OK): + self.fail('%s "%s" is not writable.' % ( + self.path_type, + filename_to_ui(value) + ), param, ctx) + if self.readable and not os.access(value, os.R_OK): + self.fail('%s "%s" is not readable.' % ( + self.path_type, + filename_to_ui(value) + ), param, ctx) return self.coerce_path_result(rv) diff --git a/examples/.DS_Store b/examples/.DS_Store deleted file mode 100644 index a0cf9ee..0000000 Binary files a/examples/.DS_Store and /dev/null differ diff --git a/examples/demo/demo.py b/examples/demo/demo.py deleted file mode 100644 index c02ff33..0000000 --- a/examples/demo/demo.py +++ /dev/null @@ -1,47 +0,0 @@ -import click - - -class VcsContext(object): - - def __init__(self): - self.debug = False - - -class FancyContext(object): - - def __init__(self): - pass - - -pass_vcs = click.make_pass_decorator(VcsContext, ensure=True) -pass_fancy = click.make_pass_decorator(FancyContext, ensure=True) - - -@click.group() -@pass_vcs -def cli(obj): - """Write stuff here.""" - print obj - - -@click.group() -@pass_vcs -def commit(obj): - """This commits some stuff.""" - print obj - - -@click.command() -@pass_fancy -def fancy_thing(obj): - ctx = click.get_current_context() - print obj - print 'find vcs context', ctx.find_object(VcsContext) - - -cli.add_command(commit) -commit.add_command(fancy_thing) - - -if __name__ == '__main__': - cli() diff --git a/examples/imagepipe/.DS_Store b/examples/imagepipe/.DS_Store deleted file mode 100644 index ea27d0d..0000000 Binary files a/examples/imagepipe/.DS_Store and /dev/null differ diff --git a/examples/imagepipe/click_example_imagepipe.egg-info/PKG-INFO b/examples/imagepipe/click_example_imagepipe.egg-info/PKG-INFO deleted file mode 100644 index 9cde7e6..0000000 --- a/examples/imagepipe/click_example_imagepipe.egg-info/PKG-INFO +++ /dev/null @@ -1,10 +0,0 @@ -Metadata-Version: 1.0 -Name: click-example-imagepipe -Version: 1.0 -Summary: UNKNOWN -Home-page: UNKNOWN -Author: UNKNOWN -Author-email: UNKNOWN -License: UNKNOWN -Description: UNKNOWN -Platform: UNKNOWN diff --git a/examples/imagepipe/click_example_imagepipe.egg-info/SOURCES.txt b/examples/imagepipe/click_example_imagepipe.egg-info/SOURCES.txt deleted file mode 100644 index 10372d6..0000000 --- a/examples/imagepipe/click_example_imagepipe.egg-info/SOURCES.txt +++ /dev/null @@ -1,8 +0,0 @@ -README -imagepipe.py -click_example_imagepipe.egg-info/PKG-INFO -click_example_imagepipe.egg-info/SOURCES.txt -click_example_imagepipe.egg-info/dependency_links.txt -click_example_imagepipe.egg-info/entry_points.txt -click_example_imagepipe.egg-info/requires.txt -click_example_imagepipe.egg-info/top_level.txt \ No newline at end of file diff --git a/examples/imagepipe/click_example_imagepipe.egg-info/entry_points.txt b/examples/imagepipe/click_example_imagepipe.egg-info/entry_points.txt deleted file mode 100644 index 2ed4423..0000000 --- a/examples/imagepipe/click_example_imagepipe.egg-info/entry_points.txt +++ /dev/null @@ -1,4 +0,0 @@ - - [console_scripts] - imagepipe=imagepipe:cli - \ No newline at end of file diff --git a/examples/imagepipe/click_example_imagepipe.egg-info/requires.txt b/examples/imagepipe/click_example_imagepipe.egg-info/requires.txt deleted file mode 100644 index 4d441ba..0000000 --- a/examples/imagepipe/click_example_imagepipe.egg-info/requires.txt +++ /dev/null @@ -1 +0,0 @@ -Click \ No newline at end of file diff --git a/examples/imagepipe/click_example_imagepipe.egg-info/top_level.txt b/examples/imagepipe/click_example_imagepipe.egg-info/top_level.txt deleted file mode 100644 index c7f8dcb..0000000 --- a/examples/imagepipe/click_example_imagepipe.egg-info/top_level.txt +++ /dev/null @@ -1 +0,0 @@ -imagepipe diff --git a/examples/naval/click_example_naval.egg-info/SOURCES.txt b/examples/naval/click_example_naval.egg-info/SOURCES.txt deleted file mode 100644 index 4cd72f5..0000000 --- a/examples/naval/click_example_naval.egg-info/SOURCES.txt +++ /dev/null @@ -1,8 +0,0 @@ -README -naval.py -click_example_naval.egg-info/PKG-INFO -click_example_naval.egg-info/SOURCES.txt -click_example_naval.egg-info/dependency_links.txt -click_example_naval.egg-info/entry_points.txt -click_example_naval.egg-info/requires.txt -click_example_naval.egg-info/top_level.txt \ No newline at end of file diff --git a/examples/naval/click_example_naval.egg-info/entry_points.txt b/examples/naval/click_example_naval.egg-info/entry_points.txt deleted file mode 100644 index 3be14b0..0000000 --- a/examples/naval/click_example_naval.egg-info/entry_points.txt +++ /dev/null @@ -1,4 +0,0 @@ - - [console_scripts] - naval=naval:cli - \ No newline at end of file diff --git a/examples/naval/click_example_naval.egg-info/requires.txt b/examples/naval/click_example_naval.egg-info/requires.txt deleted file mode 100644 index b98f660..0000000 --- a/examples/naval/click_example_naval.egg-info/requires.txt +++ /dev/null @@ -1 +0,0 @@ -click \ No newline at end of file diff --git a/examples/naval/click_example_naval.egg-info/top_level.txt b/examples/naval/click_example_naval.egg-info/top_level.txt deleted file mode 100644 index 5a52231..0000000 --- a/examples/naval/click_example_naval.egg-info/top_level.txt +++ /dev/null @@ -1 +0,0 @@ -naval diff --git a/examples/repo/click_example_repo.egg-info/PKG-INFO b/examples/plugins/BrokenPlugin/printer_bold.egg-info/PKG-INFO similarity index 80% rename from examples/repo/click_example_repo.egg-info/PKG-INFO rename to examples/plugins/BrokenPlugin/printer_bold.egg-info/PKG-INFO index a38df1f..97a4724 100644 --- a/examples/repo/click_example_repo.egg-info/PKG-INFO +++ b/examples/plugins/BrokenPlugin/printer_bold.egg-info/PKG-INFO @@ -1,6 +1,6 @@ Metadata-Version: 1.0 -Name: click-example-repo -Version: 0.1 +Name: printer-bold +Version: 0.1dev0 Summary: UNKNOWN Home-page: UNKNOWN Author: UNKNOWN diff --git a/examples/plugins/BrokenPlugin/printer_bold.egg-info/SOURCES.txt b/examples/plugins/BrokenPlugin/printer_bold.egg-info/SOURCES.txt new file mode 100644 index 0000000..34aba44 --- /dev/null +++ b/examples/plugins/BrokenPlugin/printer_bold.egg-info/SOURCES.txt @@ -0,0 +1,8 @@ +README.rst +printer_bold/__init__.py +printer_bold/core.py +printer_bold.egg-info/PKG-INFO +printer_bold.egg-info/SOURCES.txt +printer_bold.egg-info/dependency_links.txt +printer_bold.egg-info/entry_points.txt +printer_bold.egg-info/top_level.txt \ No newline at end of file diff --git a/examples/imagepipe/click_example_imagepipe.egg-info/dependency_links.txt b/examples/plugins/BrokenPlugin/printer_bold.egg-info/dependency_links.txt similarity index 100% rename from examples/imagepipe/click_example_imagepipe.egg-info/dependency_links.txt rename to examples/plugins/BrokenPlugin/printer_bold.egg-info/dependency_links.txt diff --git a/examples/plugins/BrokenPlugin/printer_bold.egg-info/entry_points.txt b/examples/plugins/BrokenPlugin/printer_bold.egg-info/entry_points.txt new file mode 100644 index 0000000..1635389 --- /dev/null +++ b/examples/plugins/BrokenPlugin/printer_bold.egg-info/entry_points.txt @@ -0,0 +1,4 @@ + + [printer.plugins] + bold=printer_bold.core:bolddddddddddd + \ No newline at end of file diff --git a/examples/plugins/BrokenPlugin/printer_bold.egg-info/top_level.txt b/examples/plugins/BrokenPlugin/printer_bold.egg-info/top_level.txt new file mode 100644 index 0000000..be45b4b --- /dev/null +++ b/examples/plugins/BrokenPlugin/printer_bold.egg-info/top_level.txt @@ -0,0 +1 @@ +printer_bold diff --git a/examples/naval/click_example_naval.egg-info/PKG-INFO b/examples/plugins/printer.egg-info/PKG-INFO similarity index 79% rename from examples/naval/click_example_naval.egg-info/PKG-INFO rename to examples/plugins/printer.egg-info/PKG-INFO index cf213e5..7f22902 100644 --- a/examples/naval/click_example_naval.egg-info/PKG-INFO +++ b/examples/plugins/printer.egg-info/PKG-INFO @@ -1,6 +1,6 @@ Metadata-Version: 1.0 -Name: click-example-naval -Version: 2.0 +Name: printer +Version: 0.1dev0 Summary: UNKNOWN Home-page: UNKNOWN Author: UNKNOWN diff --git a/examples/plugins/printer.egg-info/SOURCES.txt b/examples/plugins/printer.egg-info/SOURCES.txt new file mode 100644 index 0000000..a1d305e --- /dev/null +++ b/examples/plugins/printer.egg-info/SOURCES.txt @@ -0,0 +1,8 @@ +README.rst +printer/__init__.py +printer/cli.py +printer.egg-info/PKG-INFO +printer.egg-info/SOURCES.txt +printer.egg-info/dependency_links.txt +printer.egg-info/entry_points.txt +printer.egg-info/top_level.txt \ No newline at end of file diff --git a/examples/naval/click_example_naval.egg-info/dependency_links.txt b/examples/plugins/printer.egg-info/dependency_links.txt similarity index 100% rename from examples/naval/click_example_naval.egg-info/dependency_links.txt rename to examples/plugins/printer.egg-info/dependency_links.txt diff --git a/examples/plugins/printer.egg-info/entry_points.txt b/examples/plugins/printer.egg-info/entry_points.txt new file mode 100644 index 0000000..f2e6982 --- /dev/null +++ b/examples/plugins/printer.egg-info/entry_points.txt @@ -0,0 +1,4 @@ + + [console_scripts] + printer=printer.cli:cli + \ No newline at end of file diff --git a/examples/plugins/printer.egg-info/top_level.txt b/examples/plugins/printer.egg-info/top_level.txt new file mode 100644 index 0000000..24b8a4f --- /dev/null +++ b/examples/plugins/printer.egg-info/top_level.txt @@ -0,0 +1 @@ +printer diff --git a/examples/repo/click_example_repo.egg-info/SOURCES.txt b/examples/repo/click_example_repo.egg-info/SOURCES.txt deleted file mode 100644 index dca6e07..0000000 --- a/examples/repo/click_example_repo.egg-info/SOURCES.txt +++ /dev/null @@ -1,8 +0,0 @@ -README -repo.py -click_example_repo.egg-info/PKG-INFO -click_example_repo.egg-info/SOURCES.txt -click_example_repo.egg-info/dependency_links.txt -click_example_repo.egg-info/entry_points.txt -click_example_repo.egg-info/requires.txt -click_example_repo.egg-info/top_level.txt \ No newline at end of file diff --git a/examples/repo/click_example_repo.egg-info/dependency_links.txt b/examples/repo/click_example_repo.egg-info/dependency_links.txt deleted file mode 100644 index 8b13789..0000000 --- a/examples/repo/click_example_repo.egg-info/dependency_links.txt +++ /dev/null @@ -1 +0,0 @@ - diff --git a/examples/repo/click_example_repo.egg-info/entry_points.txt b/examples/repo/click_example_repo.egg-info/entry_points.txt deleted file mode 100644 index 2399f14..0000000 --- a/examples/repo/click_example_repo.egg-info/entry_points.txt +++ /dev/null @@ -1,4 +0,0 @@ - - [console_scripts] - repo=repo:cli - \ No newline at end of file diff --git a/examples/repo/click_example_repo.egg-info/requires.txt b/examples/repo/click_example_repo.egg-info/requires.txt deleted file mode 100644 index b98f660..0000000 --- a/examples/repo/click_example_repo.egg-info/requires.txt +++ /dev/null @@ -1 +0,0 @@ -click \ No newline at end of file diff --git a/examples/repo/click_example_repo.egg-info/top_level.txt b/examples/repo/click_example_repo.egg-info/top_level.txt deleted file mode 100644 index f606d5e..0000000 --- a/examples/repo/click_example_repo.egg-info/top_level.txt +++ /dev/null @@ -1 +0,0 @@ -repo diff --git a/examples/termui/build/lib/termui.py b/examples/termui/build/lib/termui.py new file mode 100644 index 0000000..007ac42 --- /dev/null +++ b/examples/termui/build/lib/termui.py @@ -0,0 +1,145 @@ +# coding: utf-8 +import click +import time +import random + +try: + range_type = xrange +except NameError: + range_type = range + + +@click.group() +def cli(): + """This script showcases different terminal UI helpers in Click.""" + pass + + +@cli.command() +def colordemo(): + """Demonstrates ANSI color support.""" + for color in 'red', 'green', 'blue': + click.echo(click.style('I am colored %s' % color, fg=color)) + click.echo(click.style('I am background colored %s' % color, bg=color)) + + +@cli.command() +def pager(): + """Demonstrates using the pager.""" + lines = [] + for x in range_type(200): + lines.append('%s. Hello World!' % click.style(str(x), fg='green')) + click.echo_via_pager('\n'.join(lines)) + + +@cli.command() +@click.option('--count', default=8000, type=click.IntRange(1, 100000), + help='The number of items to process.') +def progress(count): + """Demonstrates the progress bar.""" + items = range_type(count) + + def process_slowly(item): + time.sleep(0.002 * random.random()) + + def filter(items): + for item in items: + if random.random() > 0.3: + yield item + + with click.progressbar(items, label='Processing accounts', + fill_char=click.style('#', fg='green')) as bar: + for item in bar: + process_slowly(item) + + def show_item(item): + if item is not None: + return 'Item #%d' % item + + with click.progressbar(filter(items), label='Committing transaction', + fill_char=click.style('#', fg='yellow'), + item_show_func=show_item) as bar: + for item in bar: + process_slowly(item) + + with click.progressbar(length=count, label='Counting', + bar_template='%(label)s %(bar)s | %(info)s', + fill_char=click.style(u'█', fg='cyan'), + empty_char=' ') as bar: + for item in bar: + process_slowly(item) + + with click.progressbar(length=count, width=0, show_percent=False, + show_eta=False, + fill_char=click.style('#', fg='magenta')) as bar: + for item in bar: + process_slowly(item) + + +@cli.command() +@click.argument('url') +def open(url): + """Opens a file or URL In the default application.""" + click.launch(url) + + +@cli.command() +@click.argument('url') +def locate(url): + """Opens a file or URL In the default application.""" + click.launch(url, locate=True) + + +@cli.command() +def edit(): + """Opens an editor with some text in it.""" + MARKER = '# Everything below is ignored\n' + message = click.edit('\n\n' + MARKER) + if message is not None: + msg = message.split(MARKER, 1)[0].rstrip('\n') + if not msg: + click.echo('Empty message!') + else: + click.echo('Message:\n' + msg) + else: + click.echo('You did not enter anything!') + + +@cli.command() +def clear(): + """Clears the entire screen.""" + click.clear() + + +@cli.command() +def pause(): + """Waits for the user to press a button.""" + click.pause() + + +@cli.command() +def menu(): + """Shows a simple menu.""" + menu = 'main' + while 1: + if menu == 'main': + click.echo('Main menu:') + click.echo(' d: debug menu') + click.echo(' q: quit') + char = click.getchar() + if char == 'd': + menu = 'debug' + elif char == 'q': + menu = 'quit' + else: + click.echo('Invalid input') + elif menu == 'debug': + click.echo('Debug menu') + click.echo(' b: back') + char = click.getchar() + if char == 'b': + menu = 'main' + else: + click.echo('Invalid input') + elif menu == 'quit': + return diff --git a/examples/termui/click_example_termui.egg-info/PKG-INFO b/examples/termui/click_example_termui.egg-info/PKG-INFO deleted file mode 100644 index 46801c5..0000000 --- a/examples/termui/click_example_termui.egg-info/PKG-INFO +++ /dev/null @@ -1,10 +0,0 @@ -Metadata-Version: 1.0 -Name: click-example-termui -Version: 1.0 -Summary: UNKNOWN -Home-page: UNKNOWN -Author: UNKNOWN -Author-email: UNKNOWN -License: UNKNOWN -Description: UNKNOWN -Platform: UNKNOWN diff --git a/examples/termui/click_example_termui.egg-info/SOURCES.txt b/examples/termui/click_example_termui.egg-info/SOURCES.txt deleted file mode 100644 index 35c0608..0000000 --- a/examples/termui/click_example_termui.egg-info/SOURCES.txt +++ /dev/null @@ -1,8 +0,0 @@ -README -termui.py -click_example_termui.egg-info/PKG-INFO -click_example_termui.egg-info/SOURCES.txt -click_example_termui.egg-info/dependency_links.txt -click_example_termui.egg-info/entry_points.txt -click_example_termui.egg-info/requires.txt -click_example_termui.egg-info/top_level.txt \ No newline at end of file diff --git a/examples/termui/click_example_termui.egg-info/dependency_links.txt b/examples/termui/click_example_termui.egg-info/dependency_links.txt deleted file mode 100644 index 8b13789..0000000 --- a/examples/termui/click_example_termui.egg-info/dependency_links.txt +++ /dev/null @@ -1 +0,0 @@ - diff --git a/examples/termui/click_example_termui.egg-info/entry_points.txt b/examples/termui/click_example_termui.egg-info/entry_points.txt deleted file mode 100644 index 0abfdb5..0000000 --- a/examples/termui/click_example_termui.egg-info/entry_points.txt +++ /dev/null @@ -1,4 +0,0 @@ - - [console_scripts] - termui=termui:cli - \ No newline at end of file diff --git a/examples/termui/click_example_termui.egg-info/requires.txt b/examples/termui/click_example_termui.egg-info/requires.txt deleted file mode 100644 index 34ba309..0000000 --- a/examples/termui/click_example_termui.egg-info/requires.txt +++ /dev/null @@ -1,2 +0,0 @@ -click -colorama \ No newline at end of file diff --git a/examples/termui/click_example_termui.egg-info/top_level.txt b/examples/termui/click_example_termui.egg-info/top_level.txt deleted file mode 100644 index 7476d1f..0000000 --- a/examples/termui/click_example_termui.egg-info/top_level.txt +++ /dev/null @@ -1 +0,0 @@ -termui diff --git a/examples/termui/dist/click_example_termui-1.0-py3.4.egg b/examples/termui/dist/click_example_termui-1.0-py3.4.egg new file mode 100644 index 0000000..4bb967c Binary files /dev/null and b/examples/termui/dist/click_example_termui-1.0-py3.4.egg differ diff --git a/tests/test_arguments.py b/tests/test_arguments.py index 751ca69..1972976 100644 --- a/tests/test_arguments.py +++ b/tests/test_arguments.py @@ -106,6 +106,17 @@ def test_file_args(runner): assert result.exit_code == 0 +def test_path_args(runner): + @click.command() + @click.argument('input', type=click.Path(dir_okay=False, allow_dash=True)) + def foo(input): + click.echo(input) + + result = runner.invoke(foo, ['-']) + assert result.output == '-\n' + assert result.exit_code == 0 + + def test_file_atomics(runner): @click.command() @click.argument('output', type=click.File('wb', atomic=True)) diff --git a/tests/test_bashcomplete.py b/tests/test_bashcomplete.py new file mode 100644 index 0000000..f75a236 --- /dev/null +++ b/tests/test_bashcomplete.py @@ -0,0 +1,20 @@ +# -*- coding: utf-8 -*- + +import click +from click._bashcomplete import get_choices + +def test_basic(): + @click.group() + @click.option('--global-opt') + def cli(global_opt): + pass + + @cli.command() + @click.option('--local-opt') + def sub(local_opt): + pass + + assert list(get_choices(cli, 'lol', [], '')) == ['sub'] + assert list(get_choices(cli, 'lol', [], '-')) == ['--global-opt'] + assert list(get_choices(cli, 'lol', ['sub'], '')) == [] + assert list(get_choices(cli, 'lol', ['sub'], '-')) == ['--local-opt']