kiwi-scp/kiwi_scp/commands/cli.py

102 lines
3.1 KiB
Python
Raw Normal View History

import os
2021-11-03 15:32:01 +00:00
import sys
2021-11-02 16:21:01 +00:00
from enum import Enum, auto
2021-11-03 16:58:18 +00:00
from typing import List, Tuple, Iterable, Any, Type
import click
2021-11-06 02:45:27 +00:00
from ..instance import Instance, Project, Services
2021-10-29 11:37:59 +00:00
class KiwiCLI(click.MultiCommand):
"""Command Line Interface spread over multiple files in this directory"""
def list_commands(self, ctx):
"""list all the commands defined by cmd_*.py files in this directory"""
return (
filename[4:-3]
for filename in os.listdir(os.path.abspath(os.path.dirname(__file__)))
if filename.startswith("cmd_") and filename.endswith(".py")
)
def get_command(self, ctx, name):
"""import and return a specific command"""
try:
2021-11-03 00:12:32 +00:00
mod = __import__(f"kiwi_scp.commands.cmd_{name}", None, None, ["CMD"])
except ImportError:
return
2021-11-02 16:21:01 +00:00
return mod.CMD
class KiwiCommand:
2021-11-03 15:32:01 +00:00
@staticmethod
def print_multi_color(*content: Tuple[str, str]):
for message, color in content:
click.secho(message, fg=color, nl=False)
click.echo()
@staticmethod
def print_header(header: str):
click.secho(header, fg="green", bold=True)
@staticmethod
2021-11-06 02:45:27 +00:00
def print_error(error: str):
click.secho(error, file=sys.stderr, fg="red", bold=True)
2021-11-03 15:32:01 +00:00
@staticmethod
def print_list(content: Iterable[str]):
for item in content:
KiwiCommand.print_multi_color(
(" - ", "green"),
(item, "blue"),
)
2021-11-03 16:58:18 +00:00
@staticmethod
def user_query(description: str, default: Any, cast_to: Type[Any] = str):
# prompt user as per argument
while True:
try:
prompt = \
click.style(f"Enter {description} [", fg="green") + \
click.style(default, fg="blue") + \
click.style("] ", fg="green")
str_value = input(prompt).strip()
if str_value:
return cast_to(str_value)
else:
return default
except EOFError:
click.echo("Input aborted.")
return default
except Exception as e:
click.echo(f"Invalid input: {e}")
2021-11-02 16:21:01 +00:00
@classmethod
2021-11-03 00:12:32 +00:00
def run_for_instance(cls, instance: Instance, **kwargs) -> None:
2021-11-06 02:45:27 +00:00
for project_config in instance.config.projects:
project = instance.get_project(project_config.name)
cls.run_for_existing_project(instance, project, **kwargs)
2021-11-02 16:21:01 +00:00
@classmethod
2021-11-06 02:45:27 +00:00
def run_for_new_project(cls, instance: Instance, project_name: str, **kwargs) -> None:
raise Exception
2021-11-03 15:32:01 +00:00
2021-11-06 02:45:27 +00:00
@classmethod
def run_for_existing_project(cls, instance: Instance, project: Project, **kwargs) -> None:
service_names = [service.name for service in project.services.content]
cls.run_for_services(instance, project, service_names, **kwargs)
2021-11-02 16:21:01 +00:00
@classmethod
2021-11-06 02:45:27 +00:00
def run_for_services(cls, instance: Instance, project: Project, service_names: List[str], **kwargs) -> None:
raise Exception
2021-11-02 16:21:01 +00:00
class KiwiCommandType(Enum):
INSTANCE = auto()
PROJECT = auto()
SERVICE = auto()