first commit
This commit is contained in:
@@ -0,0 +1,25 @@
|
||||
"""Keep tests from picking up a real ~/.gpu-rent/.env or OS_* from the shell."""
|
||||
|
||||
import pytest
|
||||
|
||||
|
||||
OS_KEYS = (
|
||||
"OS_AUTH_URL",
|
||||
"OS_USER_DOMAIN_NAME",
|
||||
"OS_USERNAME",
|
||||
"OS_PASSWORD",
|
||||
"OS_PROJECT_ID",
|
||||
"OS_REGION_NAME",
|
||||
"GPU_RENT_AZ",
|
||||
"CIVITAI_API_TOKEN",
|
||||
)
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def isolate_home(tmp_path, monkeypatch):
|
||||
monkeypatch.setenv("HOME", str(tmp_path))
|
||||
monkeypatch.setenv("USERPROFILE", str(tmp_path))
|
||||
monkeypatch.chdir(tmp_path)
|
||||
for key in OS_KEYS:
|
||||
monkeypatch.delenv(key, raising=False)
|
||||
return tmp_path
|
||||
@@ -0,0 +1,24 @@
|
||||
from typer.testing import CliRunner
|
||||
|
||||
from gpu_rent.cli import app
|
||||
|
||||
runner = CliRunner()
|
||||
|
||||
|
||||
def test_help():
|
||||
result = runner.invoke(app, ["--help"])
|
||||
assert result.exit_code == 0
|
||||
assert "doctor" in result.stdout
|
||||
|
||||
|
||||
def test_version():
|
||||
result = runner.invoke(app, ["version"])
|
||||
assert result.exit_code == 0
|
||||
assert "0.1.0" in result.stdout
|
||||
|
||||
|
||||
def test_up_nyi_after_missing_env(monkeypatch, tmp_path):
|
||||
monkeypatch.setenv("HOME", str(tmp_path))
|
||||
monkeypatch.setenv("USERPROFILE", str(tmp_path))
|
||||
result = runner.invoke(app, ["up"])
|
||||
assert result.exit_code != 0
|
||||
@@ -0,0 +1,34 @@
|
||||
from gpu_rent.config import load_config
|
||||
from gpu_rent.ssh_keys import ensure_ed25519, public_path
|
||||
|
||||
|
||||
def test_load_config_missing_auth(monkeypatch, tmp_path):
|
||||
monkeypatch.setenv("HOME", str(tmp_path))
|
||||
monkeypatch.setenv("USERPROFILE", str(tmp_path))
|
||||
for key in (
|
||||
"OS_AUTH_URL",
|
||||
"OS_USER_DOMAIN_NAME",
|
||||
"OS_USERNAME",
|
||||
"OS_PASSWORD",
|
||||
"OS_PROJECT_ID",
|
||||
"OS_REGION_NAME",
|
||||
"GPU_RENT_AZ",
|
||||
):
|
||||
monkeypatch.delenv(key, raising=False)
|
||||
cfg = load_config(require_auth=False)
|
||||
assert not cfg.auth_ok
|
||||
assert "OS_USERNAME" in cfg.missing
|
||||
assert cfg.data_volume_size_gb == 100
|
||||
|
||||
|
||||
def test_ssh_key_generate(tmp_path):
|
||||
private = tmp_path / "id_ed25519"
|
||||
got, pub = ensure_ed25519(private)
|
||||
assert got == private
|
||||
assert pub == public_path(private)
|
||||
assert private.is_file()
|
||||
assert pub.is_file()
|
||||
text = pub.read_text(encoding="utf-8")
|
||||
assert text.startswith("ssh-ed25519")
|
||||
ensure_ed25519(private)
|
||||
assert private.read_bytes()
|
||||
@@ -0,0 +1,57 @@
|
||||
from gpu_rent.inventory import (
|
||||
gpu_boot_image_score,
|
||||
gpu_quota_from_compute,
|
||||
match_label,
|
||||
pick_boot_image,
|
||||
rank_flavors,
|
||||
)
|
||||
|
||||
|
||||
class FakeFlavor:
|
||||
def __init__(self, flavor_id: str, name: str, extra=None, disabled: bool = False):
|
||||
self.id = flavor_id
|
||||
self.name = name
|
||||
self.extra_specs = extra or {}
|
||||
self.is_disabled = disabled
|
||||
self.vcpus = 8
|
||||
self.ram = 32768
|
||||
|
||||
|
||||
def test_match_4090_24_not_48():
|
||||
a = FakeFlavor("1", "GPU 1x RTX 4090 24GB")
|
||||
b = FakeFlavor("2", "GPU 1x RTX 4090 48GB")
|
||||
assert match_label("4090-24", a)
|
||||
assert not match_label("4090-24", b)
|
||||
assert match_label("4090-48", b)
|
||||
|
||||
|
||||
def test_rank_skips_disabled():
|
||||
flavors = [
|
||||
FakeFlavor("d", "RTX 4090 24GB", disabled=True),
|
||||
FakeFlavor("ok", "RTX A5000 24GB"),
|
||||
]
|
||||
ranked = rank_flavors(flavors, ("4090-24", "a5000"))
|
||||
assert [x.id for x in ranked] == ["ok"]
|
||||
assert ranked[0].label == "a5000"
|
||||
|
||||
|
||||
def test_gpu_quota_from_compute():
|
||||
assert gpu_quota_from_compute({"cores": 10}) is None
|
||||
assert gpu_quota_from_compute({"gpu": 0}) == 0
|
||||
assert gpu_quota_from_compute({"GPU_limit": 2}) == 2
|
||||
|
||||
|
||||
def test_pick_boot_image_prefers_24_580_without_docker():
|
||||
class Img:
|
||||
def __init__(self, name):
|
||||
self.name = name
|
||||
|
||||
images = [
|
||||
Img("Ubuntu 24.04 LTS 64-bit GPU Driver 580 Docker"),
|
||||
Img("Ubuntu 24.04 LTS 64-bit GPU Driver 535"),
|
||||
Img("Ubuntu 24.04 LTS 64-bit GPU Driver 580"),
|
||||
Img("Data Science VM (Ubuntu 22.04 LTS 64-bit)"),
|
||||
]
|
||||
picked = pick_boot_image(images)
|
||||
assert picked.name == "Ubuntu 24.04 LTS 64-bit GPU Driver 580"
|
||||
assert gpu_boot_image_score(picked.name) > gpu_boot_image_score(images[0].name)
|
||||
@@ -0,0 +1,32 @@
|
||||
from pathlib import Path
|
||||
|
||||
from gpu_rent.manifests import parse_extensions, parse_models
|
||||
|
||||
|
||||
def test_models_skips_version_zero(tmp_path: Path):
|
||||
path = tmp_path / "models.yaml"
|
||||
path.write_text(
|
||||
"checkpoint:\n - version_id: 0\n - version_id: 123\n - url: https://civitai.red/models/1?modelVersionId=9\n",
|
||||
encoding="utf-8",
|
||||
)
|
||||
entries = parse_models(path)
|
||||
assert len(entries) == 2
|
||||
assert entries[0].version_id == 123
|
||||
assert entries[1].url.endswith("9")
|
||||
|
||||
|
||||
def test_extensions_empty_file(tmp_path: Path):
|
||||
path = tmp_path / "extensions.yaml"
|
||||
path.write_text("swarmui: []\ncomfy: []\n", encoding="utf-8")
|
||||
assert parse_extensions(path) == []
|
||||
|
||||
|
||||
def test_extensions_repo(tmp_path: Path):
|
||||
path = tmp_path / "extensions.yaml"
|
||||
path.write_text(
|
||||
"swarmui:\n - url: https://github.com/org/Ext.git\n ref: main\n dir: Ext\n",
|
||||
encoding="utf-8",
|
||||
)
|
||||
repos = parse_extensions(path)
|
||||
assert repos[0].kind == "swarmui"
|
||||
assert repos[0].directory == "Ext"
|
||||
Reference in New Issue
Block a user