import sys import click import pytest def debug(): click.echo('%s=%s' % ( sys._getframe(1).f_code.co_name, '|'.join(click.get_current_context().args), )) def test_basic_chaining(runner): @click.group(chain=True) def cli(): pass @cli.command('sdist') def sdist(): click.echo('sdist called') @cli.command('bdist') def bdist(): click.echo('bdist called') result = runner.invoke(cli, ['bdist', 'sdist', 'bdist']) assert not result.exception assert result.output.splitlines() == [ 'bdist called', 'sdist called', 'bdist called', ] def test_chaining_help(runner): @click.group(chain=True) def cli(): """ROOT HELP""" pass @cli.command('sdist') def sdist(): """SDIST HELP""" click.echo('sdist called') @cli.command('bdist') def bdist(): """BDIST HELP""" click.echo('bdist called') result = runner.invoke(cli, ['--help']) assert not result.exception assert 'COMMAND1 [ARGS]... [COMMAND2 [ARGS]...]...' in result.output assert 'ROOT HELP' in result.output result = runner.invoke(cli, ['sdist', '--help']) assert not result.exception assert 'SDIST HELP' in result.output result = runner.invoke(cli, ['bdist', '--help']) assert not result.exception assert 'BDIST HELP' in result.output result = runner.invoke(cli, ['bdist', 'sdist', '--help']) assert not result.exception assert 'SDIST HELP' in result.output def test_chaining_with_options(runner): @click.group(chain=True) def cli(): pass @cli.command('sdist') @click.option('--format') def sdist(format): click.echo('sdist called %s' % format) @cli.command('bdist') @click.option('--format') def bdist(format): click.echo('bdist called %s' % format) result = runner.invoke(cli, ['bdist', '--format=1', 'sdist', '--format=2']) assert not result.exception assert result.output.splitlines() == [ 'bdist called 1', 'sdist called 2', ] def test_chaining_with_arguments(runner): @click.group(chain=True) def cli(): pass @cli.command('sdist') @click.argument('format') def sdist(format): click.echo('sdist called %s' % format) @cli.command('bdist') @click.argument('format') def bdist(format): click.echo('bdist called %s' % format) result = runner.invoke(cli, ['bdist', '1', 'sdist', '2']) assert not result.exception assert result.output.splitlines() == [ 'bdist called 1', 'sdist called 2', ] def test_pipeline(runner): @click.group(chain=True, invoke_without_command=True) @click.option('-i', '--input', type=click.File('r')) def cli(input): pass @cli.resultcallback() def process_pipeline(processors, input): iterator = (x.rstrip('\r\n') for x in input) for processor in processors: iterator = processor(iterator) for item in iterator: click.echo(item) @cli.command('uppercase') def make_uppercase(): def processor(iterator): for line in iterator: yield line.upper() return processor @cli.command('strip') def make_strip(): def processor(iterator): for line in iterator: yield line.strip() return processor result = runner.invoke(cli, ['-i', '-'], input='foo\nbar') assert not result.exception assert result.output.splitlines() == [ 'foo', 'bar', ] result = runner.invoke(cli, ['-i', '-', 'strip'], input='foo \n bar') assert not result.exception assert result.output.splitlines() == [ 'foo', 'bar', ] result = runner.invoke(cli, ['-i', '-', 'strip', 'uppercase'], input='foo \n bar') assert not result.exception assert result.output.splitlines() == [ 'FOO', 'BAR', ] def test_args_and_chain(runner): @click.group(chain=True) def cli(): debug() @cli.command() def a(): debug() @cli.command() def b(): debug() @cli.command() def c(): debug() result = runner.invoke(cli, ['a', 'b', 'c']) assert not result.exception assert result.output.splitlines() == [ 'cli=', 'a=', 'b=', 'c=', ] def test_multicommand_arg_behavior(runner): with pytest.raises(RuntimeError): @click.group(chain=True) @click.argument('forbidden', required=False) def bad_cli(): pass with pytest.raises(RuntimeError): @click.group(chain=True) @click.argument('forbidden', nargs=-1) def bad_cli2(): pass @click.group(chain=True) @click.argument('arg') def cli(arg): click.echo('cli:%s' % arg) @cli.command() def a(): click.echo('a') result = runner.invoke(cli, ['foo', 'a']) assert not result.exception assert result.output.splitlines() == [ 'cli:foo', 'a', ] @pytest.mark.xfail def test_multicommand_chaining(runner): @click.group(chain=True) def cli(): debug() @cli.group() def l1a(): debug() @l1a.command() def l2a(): debug() @l1a.command() def l2b(): debug() @cli.command() def l1b(): debug() result = runner.invoke(cli, ['l1a', 'l2a', 'l1b']) assert not result.exception assert result.output.splitlines() == [ 'cli=', 'l1a=', 'l2a=', 'l1b=', ]