Make sure plugins are loaded when printiung help or usages
This commit is contained in:
parent
7743b566bd
commit
886c90dd6f
6 changed files with 52 additions and 17 deletions
|
@ -3,7 +3,6 @@ import logging
|
|||
import dataclasses as dt
|
||||
|
||||
from pathlib import Path
|
||||
import sys
|
||||
from typing import Callable, Literal, TextIO, Union
|
||||
|
||||
from . import cli, shell, rules, model, ninja, const, vt100
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
import sys
|
||||
from enum import Enum
|
||||
from types import GenericAlias
|
||||
import typing as tp
|
||||
import dataclasses as dt
|
||||
import logging
|
||||
|
||||
from typing import Any, Callable, Optional, Union
|
||||
from cutekit import vt100, const
|
||||
|
@ -10,6 +10,8 @@ from cutekit import vt100, const
|
|||
|
||||
T = tp.TypeVar("T")
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
# --- Scan -------------------------------------------------------------- #
|
||||
|
||||
|
||||
|
@ -542,6 +544,7 @@ class Command:
|
|||
callable: Optional[tp.Callable] = None
|
||||
subcommands: dict[str, "Command"] = dt.field(default_factory=dict)
|
||||
populated: bool = False
|
||||
path: list[str] = dt.field(default_factory=list)
|
||||
|
||||
def _spliceArgs(self, args: list[str]) -> tuple[list[str], list[str]]:
|
||||
rest = args[:]
|
||||
|
@ -554,12 +557,12 @@ class Command:
|
|||
rest = []
|
||||
return curr, rest
|
||||
|
||||
def help(self, cmd):
|
||||
vt100.title(f"{cmd}")
|
||||
def help(self):
|
||||
vt100.title(f"{self.longName}")
|
||||
print()
|
||||
|
||||
vt100.subtitle("Usage")
|
||||
print(vt100.indent(f"{cmd}{self.usage()}"))
|
||||
print(vt100.indent(f"{' '.join(self.path)}{self.usage()}"))
|
||||
print()
|
||||
|
||||
vt100.subtitle("Description")
|
||||
|
@ -631,23 +634,38 @@ class Command:
|
|||
return sub
|
||||
raise ValueError(f"Unknown subcommand '{name}'")
|
||||
|
||||
def invoke(self, argv: list[str]):
|
||||
if self.callable:
|
||||
if self.schema:
|
||||
args = self.schema.parse(argv)
|
||||
self.callable(args)
|
||||
else:
|
||||
self.callable()
|
||||
|
||||
def eval(self, args: list[str]):
|
||||
cmd = args.pop(0)
|
||||
curr, rest = self._spliceArgs(args)
|
||||
|
||||
if "-h" in curr or "--help" in curr:
|
||||
self.help(cmd)
|
||||
if len(self.path) == 0:
|
||||
# HACK: This is a special case for the root command
|
||||
# it need to always be run because it might
|
||||
# load some plugins that will register subcommands
|
||||
# that need to be displayed in the help.
|
||||
self.invoke([])
|
||||
self.help()
|
||||
return
|
||||
|
||||
if "-u" in curr or "--usage" in curr:
|
||||
if len(self.path) == 0:
|
||||
# HACK: Same as the help flag, the root command needs to be
|
||||
# always run to load plugins
|
||||
self.invoke([])
|
||||
print("Usage: " + cmd + self.usage(), end="\n\n")
|
||||
return
|
||||
|
||||
try:
|
||||
if self.callable:
|
||||
if self.schema:
|
||||
args = self.schema.parse(curr)
|
||||
self.callable(args)
|
||||
else:
|
||||
self.callable()
|
||||
self.invoke(curr)
|
||||
|
||||
if self.subcommands:
|
||||
if len(rest) > 0:
|
||||
|
@ -692,14 +710,18 @@ def command(shortName: Optional[str], longName: str, description: str = "") -> C
|
|||
schema = Schema.extractFromCallable(fn)
|
||||
path = _splitPath(longName)
|
||||
cmd = _resolvePath(path)
|
||||
|
||||
_logger.info(f"Registering command '{'.'.join(path)}'")
|
||||
if cmd.populated:
|
||||
raise ValueError(f"Command '{longName}' is already defined")
|
||||
|
||||
cmd.shortName = shortName
|
||||
cmd.longName = len(path) > 0 and path[-1] or ""
|
||||
cmd.description = description
|
||||
cmd.schema = schema
|
||||
cmd.callable = fn
|
||||
cmd.populated = True
|
||||
cmd.path = [const.ARGV0] + path
|
||||
return fn
|
||||
|
||||
return wrap
|
||||
|
|
|
@ -565,6 +565,8 @@ class Registry(DataClassJsonMixin):
|
|||
|
||||
@staticmethod
|
||||
def load(project: Project, mixins: list[str], props: Props) -> "Registry":
|
||||
_logger.info(f"Loading model for project '{project.id}'")
|
||||
|
||||
r = Registry(project)
|
||||
r._append(project)
|
||||
|
||||
|
@ -752,8 +754,8 @@ def view(
|
|||
|
||||
|
||||
class GraphArgs(TargetArgs):
|
||||
onlyLibs: bool = cli.arg(False, "only-libs", "Show only libraries")
|
||||
showDisabled: bool = cli.arg(False, "show-disabled", "Show disabled components")
|
||||
onlyLibs: bool = cli.arg(None, "only-libs", "Show only libraries")
|
||||
showDisabled: bool = cli.arg(None, "show-disabled", "Show disabled components")
|
||||
scope: str = cli.arg(
|
||||
None, "scope", "Show only the specified component and its dependencies"
|
||||
)
|
||||
|
|
|
@ -52,7 +52,7 @@ def loadAll():
|
|||
|
||||
|
||||
class PluginsArgs:
|
||||
safemod: bool = cli.arg(None, "safemode", "disable plugin loading")
|
||||
safemod: bool = cli.arg(None, "safemode", "Disable plugin loading")
|
||||
|
||||
|
||||
def setup(args: PluginsArgs):
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
import sys
|
||||
import logging
|
||||
from typing import Optional
|
||||
import docker # type: ignore
|
||||
import os
|
||||
|
@ -6,6 +7,7 @@ import dataclasses as dt
|
|||
|
||||
from . import cli, model, shell, vt100, const
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
podPrefix = "CK__"
|
||||
projectRoot = "/project"
|
||||
|
@ -111,6 +113,7 @@ def setup(args: PodSetupArgs):
|
|||
"""
|
||||
if not args.pod:
|
||||
return
|
||||
_logger.info(f"Reincarnating into pod '{args.pod}'...")
|
||||
if isinstance(args.pod, str):
|
||||
pod = args.pod.strip()
|
||||
pod = podPrefix + pod
|
||||
|
|
|
@ -38,7 +38,12 @@ def uname() -> Uname:
|
|||
distrib = {"NAME": "Unknown"}
|
||||
|
||||
result = Uname(
|
||||
un.system, distrib["NAME"], un.node, un.release, un.version, un.machine
|
||||
un.system,
|
||||
distrib["NAME"],
|
||||
un.node,
|
||||
un.release,
|
||||
un.version,
|
||||
un.machine,
|
||||
)
|
||||
|
||||
match result.machine:
|
||||
|
@ -49,6 +54,8 @@ def uname() -> Uname:
|
|||
case _:
|
||||
pass
|
||||
|
||||
_logger.debug(f"uname: {result}")
|
||||
|
||||
return result
|
||||
|
||||
|
||||
|
@ -128,6 +135,7 @@ def wget(url: str, path: Optional[str] = None) -> str:
|
|||
)
|
||||
|
||||
if os.path.exists(path):
|
||||
_logger.debug(f"Using cached {path} for {url}")
|
||||
return path
|
||||
|
||||
_logger.debug(f"Downloading {url} to {path}")
|
||||
|
@ -292,6 +300,8 @@ def cpTree(src: str, dst: str):
|
|||
|
||||
|
||||
def cloneDir(url: str, path: str, dest: str) -> str:
|
||||
_logger.debug(f"Cloning {url} to {dest}")
|
||||
|
||||
with tempfile.TemporaryDirectory() as tmp:
|
||||
mkdir(tmp)
|
||||
exec(
|
||||
|
@ -378,7 +388,6 @@ def gzip(path: str, dest: Optional[str] = None) -> str:
|
|||
"""
|
||||
Compress a file or directory
|
||||
"""
|
||||
|
||||
if dest is None:
|
||||
dest = path + ".gz"
|
||||
|
||||
|
|
Loading…
Reference in a new issue