Click: Is it possible to set dynamic options based on a passed option/arguments?

Created on 3 Oct 2017  路  6Comments  路  Source: pallets/click

First off, I searched for a more appropriate channel to ask this question, and couldn't find any. If such a channel exist, I apologized.

I have a library that uses (or aims to use) CLI commands like so:
notifiers notify [NOTIFIER_NAME] <SPECIFIC NOTIFIER OPTION> ...

So notifier foo can have options: message, token & priority and notifier bar can have api_key, text and etc.
I know I can create a custom group that will aggregate all the notifier options together, but i was wondering if there was a more dynamic approach to this.
My gut tells me that there isn't, but i figured it was worth asking.

I currently employ a catch all solution like so:

@notifiers.command(context_settings=dict(
    ignore_unknown_options=True,
    allow_extra_args=True,
))
@click.argument('provider', type=click.Choice(all_providers()), envvar='NOTIFIERS_DEFAULT_PROVIDER')
@click.pass_context
def notify(ctx, provider):
    """Send a notification to a passed provider.

    Data should be passed via a key=value input like so:

        notifiers notify pushover token=foo user=bar message=test

    """
    p = get_notifier(provider)
    data = {}
    for item in ctx.args:
        data.update([item.split('=')])
    if 'message' not in data:
        message = click.get_text_stream('stdin').read()
        if not message:
            raise click.ClickException('\'message\' option is required. '
                                       'Either pass it explicitly or pipe into the command')
        data['message'] = message

    rsp = p.notify(**data)
    rsp.raise_on_errors()

Thanks in advance!

Most helpful comment

If anyone is interested, I successfully created it by dynamically converting objects with json schema to click groups, commands and options.
https://github.com/liiight/notifiers/pull/79

All 6 comments

You can create a custom autocompletion for an argument. See https://github.com/pallets/click/blob/master/examples/bashcompletion/bashcompletion.py

Looks interesting, i'll give it a try. Thanks!

This isn't exactly what I need. What I basically need is a group/command factory since not all values that will be used have the same commands and/or options.

There currently isn't a way to do this if I understand the issue correctly. Going to close the issue as this is more support request than bug report.

Ok, cool. I started working on my own implementation for this, i'll update here when it's done for prosperity's sake,

If anyone is interested, I successfully created it by dynamically converting objects with json schema to click groups, commands and options.
https://github.com/liiight/notifiers/pull/79

Was this page helpful?
0 / 5 - 0 ratings