Added gtk demo app
This commit is contained in:
@@ -80,7 +80,6 @@ Let's get your development environment up and running:
|
||||
|
||||
NOTE: If you have the error "@clan/colors.json" you executed `npm install`, please do not do that. `direnv reload` will handle dependency management. Please delete node_modules with `rm -rf node_modules`.
|
||||
|
||||
|
||||
9. **Start the Frontend**:
|
||||
- To start the frontend, execute:
|
||||
```bash
|
||||
|
||||
@@ -5,7 +5,7 @@ from pathlib import Path
|
||||
from types import ModuleType
|
||||
from typing import Any, Optional, Sequence
|
||||
|
||||
from . import config, flakes, machines, secrets, vms, webui
|
||||
from . import config, flakes, gtkui, machines, secrets, vms, webui
|
||||
from .custom_logger import setup_logging
|
||||
from .dirs import get_clan_flake_toplevel
|
||||
from .ssh import cli as ssh_cli
|
||||
@@ -64,6 +64,9 @@ def create_parser(prog: Optional[str] = None) -> argparse.ArgumentParser:
|
||||
|
||||
subparsers = parser.add_subparsers()
|
||||
|
||||
parser_gtkui = subparsers.add_parser("gtkui", help="start gtkui")
|
||||
gtkui.register_parser(parser_gtkui)
|
||||
|
||||
parser_flake = subparsers.add_parser(
|
||||
"flakes", help="create a clan flake inside the current directory"
|
||||
)
|
||||
|
||||
@@ -1,9 +1,8 @@
|
||||
import asyncio
|
||||
import logging
|
||||
import deal
|
||||
import shlex
|
||||
from pathlib import Path
|
||||
from typing import Any, Callable, Coroutine, Dict, NamedTuple, Optional, Awaitable
|
||||
from typing import Any, Callable, Coroutine, Dict, NamedTuple, Optional
|
||||
|
||||
from .custom_logger import get_caller
|
||||
from .errors import ClanError
|
||||
@@ -16,8 +15,8 @@ class CmdOut(NamedTuple):
|
||||
stderr: str
|
||||
cwd: Optional[Path] = None
|
||||
|
||||
@deal.raises(ClanError)
|
||||
async def run(cmd: list[str], cwd: Optional[Path] = None) -> Awaitable[CmdOut]:
|
||||
|
||||
async def run(cmd: list[str], cwd: Optional[Path] = None) -> CmdOut:
|
||||
cwd_res = None
|
||||
if cwd is not None:
|
||||
if not cwd.exists():
|
||||
@@ -52,7 +51,6 @@ stdout:
|
||||
return CmdOut(stdout.decode("utf-8"), stderr.decode("utf-8"), cwd=cwd)
|
||||
|
||||
|
||||
@deal.raises(ClanError)
|
||||
def runforcli(
|
||||
func: Callable[..., Coroutine[Any, Any, Dict[str, CmdOut]]], *args: Any
|
||||
) -> None:
|
||||
|
||||
10
pkgs/clan-cli/clan_cli/gtkui/__init__.py
Normal file
10
pkgs/clan-cli/clan_cli/gtkui/__init__.py
Normal file
@@ -0,0 +1,10 @@
|
||||
import argparse
|
||||
from typing import Callable, Optional
|
||||
|
||||
start_app: Optional[Callable] = None
|
||||
|
||||
from .app import start_app
|
||||
|
||||
|
||||
def register_parser(parser: argparse.ArgumentParser) -> None:
|
||||
parser.set_defaults(func=start_app)
|
||||
49
pkgs/clan-cli/clan_cli/gtkui/app.glade
Normal file
49
pkgs/clan-cli/clan_cli/gtkui/app.glade
Normal file
@@ -0,0 +1,49 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.40.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.24"/>
|
||||
<object class="GtkApplicationWindow" id="main-window">
|
||||
<property name="can-focus">False</property>
|
||||
<child>
|
||||
<object class="GtkFixed">
|
||||
<property name="name">asdasd</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
<child>
|
||||
<object class="GtkButton" id="help_button">
|
||||
<property name="label" translatable="yes">May I help you?</property>
|
||||
<property name="name">asdasd</property>
|
||||
<property name="width-request">100</property>
|
||||
<property name="height-request">80</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="receives-default">True</property>
|
||||
<property name="image-position">top</property>
|
||||
<signal name="clicked" handler="on_help_button_clicked" object="coffee_label" swapped="no"/>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="x">21</property>
|
||||
<property name="y">21</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkLabel" id="coffee_label">
|
||||
<property name="width-request">100</property>
|
||||
<property name="height-request">80</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
<property name="label" translatable="yes">Get me some coffe! </property>
|
||||
<property name="width-chars">0</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="x">178</property>
|
||||
<property name="y">120</property>
|
||||
</packing>
|
||||
</child>
|
||||
<style>
|
||||
<class name="asdasd"/>
|
||||
</style>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
||||
49
pkgs/clan-cli/clan_cli/gtkui/app.glade~
Normal file
49
pkgs/clan-cli/clan_cli/gtkui/app.glade~
Normal file
@@ -0,0 +1,49 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.40.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.24"/>
|
||||
<object class="GtkApplicationWindow" id="main-window">
|
||||
<property name="can-focus">False</property>
|
||||
<child>
|
||||
<object class="GtkFixed">
|
||||
<property name="name">asdasd</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
<child>
|
||||
<object class="GtkButton" id="help_button">
|
||||
<property name="label" translatable="yes">May I help you?</property>
|
||||
<property name="name">asdasd</property>
|
||||
<property name="width-request">100</property>
|
||||
<property name="height-request">80</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="receives-default">True</property>
|
||||
<property name="image-position">top</property>
|
||||
<signal name="clicked" handler="on_help_button_clicked" object="coffee_label" swapped="no"/>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="x">21</property>
|
||||
<property name="y">21</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkLabel" id="coffee_label">
|
||||
<property name="width-request">100</property>
|
||||
<property name="height-request">80</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">False</property>
|
||||
<property name="label" translatable="yes">Get me some coffe! </property>
|
||||
<property name="width-chars">0</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="x">178</property>
|
||||
<property name="y">120</property>
|
||||
</packing>
|
||||
</child>
|
||||
<style>
|
||||
<class name="asdasd"/>
|
||||
</style>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
||||
19
pkgs/clan-cli/clan_cli/gtkui/app.py
Normal file
19
pkgs/clan-cli/clan_cli/gtkui/app.py
Normal file
@@ -0,0 +1,19 @@
|
||||
# !/usr/bin/env python3
|
||||
|
||||
import argparse # noqa
|
||||
from pathlib import Path # noqa
|
||||
|
||||
import gi # noqa
|
||||
|
||||
gi.require_version("Gtk", "3.0") # noqa
|
||||
from gi.repository import Gtk # noqa
|
||||
|
||||
|
||||
def start_app(args: argparse.Namespace) -> None:
|
||||
builder = Gtk.Builder()
|
||||
glade_file = Path(__file__).parent / "app.glade"
|
||||
builder.add_from_file(str(glade_file))
|
||||
window = builder.get_object("main-window")
|
||||
window.show_all()
|
||||
|
||||
Gtk.main()
|
||||
@@ -2,11 +2,14 @@ import json
|
||||
import os
|
||||
import subprocess
|
||||
import tempfile
|
||||
import deal
|
||||
from pathlib import Path
|
||||
from typing import Any
|
||||
|
||||
import deal
|
||||
|
||||
from .dirs import nixpkgs_flake, nixpkgs_source
|
||||
from .errors import ClanError
|
||||
|
||||
|
||||
@deal.raises(ClanError)
|
||||
def nix_command(flags: list[str]) -> list[str]:
|
||||
@@ -25,6 +28,7 @@ def nix_flake_show(flake_url: str | Path) -> list[str]:
|
||||
]
|
||||
)
|
||||
|
||||
|
||||
@deal.raises(ClanError)
|
||||
def nix_build(
|
||||
flags: list[str],
|
||||
@@ -41,6 +45,7 @@ def nix_build(
|
||||
+ flags
|
||||
)
|
||||
|
||||
|
||||
@deal.raises(ClanError)
|
||||
def nix_config() -> dict[str, Any]:
|
||||
cmd = nix_command(["show-config", "--json"])
|
||||
@@ -51,6 +56,7 @@ def nix_config() -> dict[str, Any]:
|
||||
config[key] = value["value"]
|
||||
return config
|
||||
|
||||
|
||||
@deal.raises(ClanError)
|
||||
def nix_eval(flags: list[str]) -> list[str]:
|
||||
default_flags = nix_command(
|
||||
@@ -78,6 +84,7 @@ def nix_eval(flags: list[str]) -> list[str]:
|
||||
)
|
||||
return default_flags + flags
|
||||
|
||||
|
||||
@deal.raises(ClanError)
|
||||
def nix_shell(packages: list[str], cmd: list[str]) -> list[str]:
|
||||
# we cannot use nix-shell inside the nix sandbox
|
||||
|
||||
@@ -186,6 +186,7 @@ def get_task(uuid: UUID) -> BaseTask:
|
||||
|
||||
T = TypeVar("T", bound="BaseTask")
|
||||
|
||||
|
||||
@deal.raises(ClanError)
|
||||
def create_task(task_type: Type[T], *args: Any) -> T:
|
||||
global POOL
|
||||
|
||||
@@ -36,12 +36,17 @@
|
||||
, deal
|
||||
, rope
|
||||
, clan-core-path
|
||||
, schemathesis
|
||||
, schemathesis ? null
|
||||
}:
|
||||
let
|
||||
|
||||
dependencies = [
|
||||
argcomplete # optional dependency: if not enabled, shell completion will not work
|
||||
wrapGAppsHook
|
||||
gtk3
|
||||
glib
|
||||
gobject-introspection
|
||||
pygobject3
|
||||
];
|
||||
|
||||
pytestDependencies = runtimeDependencies ++ dependencies ++ [
|
||||
|
||||
@@ -38,6 +38,11 @@ exclude = "clan_cli.nixpkgs"
|
||||
module = "argcomplete.*"
|
||||
ignore_missing_imports = true
|
||||
|
||||
[[tool.mypy.overrides]]
|
||||
module = "gi.*"
|
||||
ignore_missing_imports = true
|
||||
|
||||
|
||||
[[tool.mypy.overrides]]
|
||||
module = "jsonschema.*"
|
||||
ignore_missing_imports = true
|
||||
@@ -58,4 +63,4 @@ ignore_missing_imports = true
|
||||
line-length = 88
|
||||
|
||||
select = [ "E", "F", "I", "N"]
|
||||
ignore = [ "E501" ]
|
||||
ignore = [ "E501", "E402" ]
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
import deal
|
||||
|
||||
from clan_cli import task_manager
|
||||
from clan_cli import async_cmd
|
||||
from clan_cli import nix
|
||||
from clan_cli import nix, task_manager
|
||||
|
||||
|
||||
@deal.cases(task_manager.get_task)
|
||||
def test_get_task(case: deal.TestCase) -> None:
|
||||
case()
|
||||
|
||||
|
||||
@deal.cases(task_manager.create_task)
|
||||
def test_create_task(case: deal.TestCase) -> None:
|
||||
case()
|
||||
@@ -17,18 +17,22 @@ def test_create_task(case: deal.TestCase) -> None:
|
||||
def test_nix_command(case: deal.TestCase) -> None:
|
||||
case()
|
||||
|
||||
|
||||
@deal.cases(nix.nix_build)
|
||||
def test_nix_build(case: deal.TestCase) -> None:
|
||||
case()
|
||||
|
||||
|
||||
@deal.cases(nix.nix_config)
|
||||
def test_nix_config(case: deal.TestCase) -> None:
|
||||
case()
|
||||
|
||||
|
||||
@deal.cases(nix.nix_eval)
|
||||
def test_nix_eval(case: deal.TestCase) -> None:
|
||||
case()
|
||||
|
||||
|
||||
@deal.cases(nix.nix_shell)
|
||||
def test_nix_shell(case: deal.TestCase) -> None:
|
||||
case()
|
||||
Reference in New Issue
Block a user