integrate webserver into cli
All checks were successful
build / test (pull_request) Successful in 19s
All checks were successful
build / test (pull_request) Successful in 19s
This commit is contained in:
parent
79c61f61c7
commit
d60548dfc4
@ -3,9 +3,9 @@ import sys
|
||||
from types import ModuleType
|
||||
from typing import Optional
|
||||
|
||||
from . import admin, secrets, update
|
||||
from . import admin, secrets, update, webui
|
||||
|
||||
# from . import admin, config, secrets, update
|
||||
# from . import admin, config, secrets, update, webui
|
||||
from .errors import ClanError
|
||||
from .ssh import cli as ssh_cli
|
||||
|
||||
@ -39,6 +39,9 @@ def main() -> None:
|
||||
)
|
||||
update.register_parser(parser_update)
|
||||
|
||||
parser_webui = subparsers.add_parser("webui", help="start webui")
|
||||
webui.register_parser(parser_webui)
|
||||
|
||||
if argcomplete:
|
||||
argcomplete.autocomplete(parser)
|
||||
|
||||
|
39
pkgs/clan-cli/clan_cli/webui/__init__.py
Normal file
39
pkgs/clan-cli/clan_cli/webui/__init__.py
Normal file
@ -0,0 +1,39 @@
|
||||
import argparse
|
||||
from typing import Callable, NoReturn, Optional
|
||||
|
||||
start_server: Optional[Callable] = None
|
||||
ServerImportError: Optional[ImportError] = None
|
||||
try:
|
||||
from .server import start_server
|
||||
except ImportError as e:
|
||||
ServerImportError = e
|
||||
|
||||
|
||||
def fastapi_is_not_installed(_: argparse.Namespace) -> NoReturn:
|
||||
assert ServerImportError is not None
|
||||
print(
|
||||
f"Dependencies for the webserver is not installed. The webui command has been disabled ({ServerImportError})"
|
||||
)
|
||||
exit(1)
|
||||
|
||||
|
||||
def register_parser(parser: argparse.ArgumentParser) -> None:
|
||||
parser.add_argument("--port", type=int, default=2979, help="Port to listen on")
|
||||
parser.add_argument("--host", type=str, default="::1", help="Host to listen on")
|
||||
parser.add_argument(
|
||||
"--no-open", action="store_true", help="Don't open the browser", default=False
|
||||
)
|
||||
parser.add_argument(
|
||||
"--reload", action="store_true", help="Don't reload on changes", default=False
|
||||
)
|
||||
parser.add_argument(
|
||||
"--log-level",
|
||||
type=str,
|
||||
default="info",
|
||||
help="Log level",
|
||||
choices=["critical", "error", "warning", "info", "debug", "trace"],
|
||||
)
|
||||
if start_server is None:
|
||||
parser.set_defaults(func=fastapi_is_not_installed)
|
||||
else:
|
||||
parser.set_defaults(func=start_server)
|
41
pkgs/clan-cli/clan_cli/webui/server.py
Normal file
41
pkgs/clan-cli/clan_cli/webui/server.py
Normal file
@ -0,0 +1,41 @@
|
||||
import argparse
|
||||
import time
|
||||
import urllib.request
|
||||
import webbrowser
|
||||
from threading import Thread
|
||||
|
||||
from fastapi import FastAPI
|
||||
|
||||
# XXX: can we dynamically load this using nix develop?
|
||||
from uvicorn import run
|
||||
|
||||
app = FastAPI()
|
||||
|
||||
|
||||
@app.get("/health")
|
||||
async def read_root() -> str:
|
||||
return "OK"
|
||||
|
||||
|
||||
def defer_open_browser(base_url: str) -> None:
|
||||
for i in range(5):
|
||||
try:
|
||||
urllib.request.urlopen(base_url + "/health")
|
||||
break
|
||||
except OSError:
|
||||
time.sleep(i)
|
||||
webbrowser.open(base_url)
|
||||
|
||||
|
||||
def start_server(args: argparse.Namespace) -> None:
|
||||
if not args.no_open:
|
||||
Thread(
|
||||
target=defer_open_browser, args=(f"http://[{args.host}]:{args.port}",)
|
||||
).start()
|
||||
run(
|
||||
"clan_cli.webui.server:app",
|
||||
host=args.host,
|
||||
port=args.port,
|
||||
log_level=args.log_level,
|
||||
reload=args.reload,
|
||||
)
|
@ -1,5 +1,7 @@
|
||||
{ age
|
||||
, argcomplete
|
||||
, fastapi
|
||||
, uvicorn
|
||||
, bubblewrap
|
||||
, installShellFiles
|
||||
, nix
|
||||
@ -22,7 +24,11 @@ let
|
||||
# evaluating the flake .#
|
||||
CLAN_OPTIONS_FILE = ./clan_cli/config/jsonschema/options.json;
|
||||
|
||||
dependencies = [ argcomplete ];
|
||||
dependencies = [
|
||||
argcomplete # optional dependency: if not enabled, shell completion will not work
|
||||
fastapi
|
||||
uvicorn # optional dependencies: if not enabled, webui subcommand will not work
|
||||
];
|
||||
|
||||
testDependencies = [
|
||||
pytest
|
||||
@ -73,7 +79,7 @@ python3.pkgs.buildPythonPackage {
|
||||
wheel
|
||||
] ++ testDependencies;
|
||||
|
||||
passthru.testDependencies = testDependencies;
|
||||
passthru.testDependencies = dependencies ++ testDependencies;
|
||||
|
||||
makeWrapperArgs = [
|
||||
"--set CLAN_FLAKE ${self}"
|
||||
|
Loading…
Reference in New Issue
Block a user