Source code for qa4sm_api.cli

import os
import click
from importlib.metadata import version

from qa4sm_api.globals import (
    DEFAULT_INSTANCE, KNOWN_INSTANCES, QA4SM_DOTRC_PATH,
    _connect_with_credentials, _write_dotrc, _load_dotrc
)
from qa4sm_api.client_api import Connection


instance_option = click.option(
    "--instance", "-i",
    default=DEFAULT_INSTANCE,
    show_default=True,
    help=(
        "QA4SM instance to send trigger the validation run on. "
        f"Common values: {', '.join(KNOWN_INSTANCES)}"
    ),
)

@click.group(short_help="QA4SM API wrapper commands.")
@click.version_option(version=version("qa4sm_api"), prog_name="QA4SM Client API")
def cli():
    pass


@cli.group(short_help="API SETUP COMMANDS, see `qa4sm api --help`.")
def api():
    """
    API setup commands
    """
    pass


@cli.group(short_help="DOWNLOAD COMMANDS, see `qa4sm download --help`.")
def download():
    """
    Download data from QA4SM.
    """
    pass


[docs] def setup_api(instance=DEFAULT_INSTANCE): """ Login to instance via username and password. Retrieve API token and store it in ~/.qa4smapirc for future use. """ click.echo(f"Logging in to: {instance}") # Prompt for credentials (password input is hidden) username = click.prompt("Username") password = click.prompt("Password", hide_input=True) # Retrieve token from the remote instance try: cred_access = _connect_with_credentials(instance, username, password) except Exception as exc: raise click.ClickException(f"Login failed: {exc}") from exc if os.path.isfile(QA4SM_DOTRC_PATH): access = _load_dotrc(QA4SM_DOTRC_PATH) if instance not in access.keys(): access[instance] = dict() access[instance]['token'] = cred_access[instance]['token'] access[instance]['username'] = username action = "Added" else: access = dict() access[instance] = {'token': cred_access[instance]['token'], 'username': username} action = "Updated" _write_dotrc(access, QA4SM_DOTRC_PATH) click.echo( click.style( f"✓ {action} token for [{instance}] in {QA4SM_DOTRC_PATH}", fg="green", ) )
@api.command("setup", short_help="Add token to `.qa4smapirc` file.") @instance_option def cli_setup(instance: str) -> None: """ Authenticate with a QA4SM instance using your username and password to retrieve and store a token for the chosen instance )in ~/.qa4smapirc. """ setup_api(instance) @api.command("check", short_help="Check whether you can access an instance with " "the stored token.") @instance_option def cli_check(instance: str) -> None: """ Authenticate with a QA4SM instance using your username and password to retrieve and store a token for the chosen instance )in ~/.qa4smapirc. """ qa4sm = Connection(instance, token='file') user = qa4sm.session.user if user is not None: click.echo(f"Success, you can now send API commands to {instance}!") else: click.echo("Failed! Please make sure you have configured your " ".qa4smapirc file correctly.") @cli.command( "validate", short_help="Start a new validation run." ) @click.argument( "CONFIG_FILE", type=click.File("r"), ) @instance_option def cli_validate(conf: str, instance: str) -> None: """ Start a validation run on QA4SM using the settings from the passed configuration. \b Arguments: CONFIG_FILE Path to the validation configuration to send. Hint: use the `qa4sm download config` command to download a template from an existing run. """ # The above docstring is written to be displayed when calling --help qa4sm = Connection(instance, token='file') response = qa4sm.run_config_validation(conf, override=None) if not response.empty: run_id = response.name click.echo(f"Validation run started. See " f"{qa4sm.session.base_url}ui/validation-result/{run_id}.") else: click.echo("No response received. No validation run started") @download.command( "config", short_help="Download validation run configuration file." ) @click.argument( "RUN_ID", type=click.STRING, ) @click.option( "--out_path", "-o", default=None, metavar="PATH", help=( "Path where the downloaded config file is stored. If not specified, " "the current working directory is used. " "[default: current directory]" ), ) @instance_option def cli_download_conf(run_id: str, out_path: str, instance: str) -> None: """ Download the cofiguration file of an existing online validation run. \b Arguments: RUN_ID Validation run ID (UUID) to download. The ID is indicated, " "e.g., in the validation run URL." """ # The above docstring is written to be displayed when calling --help out_path = out_path or os.getcwd() qa4sm = Connection(instance, token='file') conf = qa4sm.download_configuration(run_id, out_path) if conf.empty: print(f"Could not download configuration for run {run_id} from " f"{instance}. Make sure the run exists.") else: print(f"Configuration stored at " f"{os.path.join(out_path, f"{run_id}.json")}") @download.command( "results", short_help="Download validation run results file." ) @click.argument( "RUN_ID", type=click.STRING, ) @click.option( "--out_path", "-o", default=None, metavar="PATH", help=( "Path where the downloaded results are stored. If not specified, " "the current working directory is used. " "[default: current directory]" ), ) @instance_option def cli_download_results(run_id: str, out_path: str, instance: str) -> None: """ Download the configuration file of an existing online validation run. \b Arguments: RUN_ID Validation run ID (UUID) to download. The ID is indicated in the validation run URL. """ # The above docstring is written to be displayed when calling --help out_path = out_path or os.getcwd() qa4sm = Connection(instance, token='file') qa4sm.download_results(run_id, out_path, force_download=True) if __name__ == "__main__": setup_api()