Metadata-Version: 2.4
Name: iil-gpufw
Version: 0.1.1
Summary: Schmaler HTTP-Client des GPU-Lease-Arbiters (ADR-296): dreiwertiger Vertrag, fail-open, Batch-Handshake
Author-email: Achim Dehnert <achim.dehnert@iil.gmbh>
License: Proprietary
Keywords: arbiter,comfyui,gpu,lease,ollama
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Requires-Python: >=3.11
Provides-Extra: dev
Requires-Dist: pytest>=8.0; extra == 'dev'
Requires-Dist: ruff>=0.3; extra == 'dev'
Description-Content-Type: text/markdown

# iil-gpufw

Schmaler HTTP-Client des GPU-Lease-Arbiters (illustration-hub) — ADR-296 §4.5,
Auftrag [platform#2020](https://github.com/achimdehnert/platform/issues/2020).

**Normative Quelle ist der HTTP-Vertrag**, nicht dieses Paket:
`illustration-hub/docs/api/gpu-lease-vertrag.md` (v0). Strategie (Vorrang,
Karenz, Räum-Reihenfolge) bleibt serverseitig. Keine Laufzeit-Dependencies,
kein Django-Import; Config wird injiziert.

## Nutzung

```python
from gpufw import ArbiterConfig, interaktive_lease, batch_lease

config = ArbiterConfig.aus_env()  # GPU_ARBITER_URL, GPU_ARBITER_TOKEN, CF_ACCESS_*

# Interaktiv: ein Mensch wartet — BELEGT heisst ehrlich abbrechen.
with interaktive_lease(config, verbraucher="mein-cli", zweck="render x") as zusage:
    if not zusage.gewaehrt:
        raise RuntimeError(zusage.als_fehlertext())  # traegt den belegt-Marker
    arbeit()

# Batch: BELEGT heisst warten (Aufrufer-Sache); Verdraengung meldet sich
# ueber das Event — zwischen Arbeitsschritten pruefen und pausieren.
with batch_lease(config, verbraucher="text-batch", job_id="job-42") as zusage:
    if not zusage.gewaehrt:
        warte_und_versuche_spaeter(zusage.grund)
    else:
        for kapitel in arbeit_in_schritten():
            if zusage.verdraengt.is_set():
                pausieren()  # interaktive Lane hat Vorrang
                break
            verarbeite(kapitel)
```

Client-Pflichten aus dem Vertrag (fail-open, kein Bezahl-Rückfall bei BELEGT,
immer freigeben, tolerant lesen) sind in `gpufw.lease` umgesetzt und getestet
(`make test`, Stub-Arbiter, kein Netz).

## Grenzen (ehrlich)

- Fail-open heisst: ohne erreichbaren Arbiter läuft der Konsument **ohne**
  Koordination weiter (`degradiert=True` + Log). Das ist Vertragsabsicht —
  kein Handgriff darf Render/Song/Text verhindern.
- `GRANTED` ist ein Absichts-Register, keine Karten-Wahrheit: Ollama-Einzelcalls
  sind lease-frei (§4.2 Nr. 7), VRAM kann trotzdem belegt sein.

## Release

Über den etablierten `/release`-Weg (ADR-084-Muster). PyPI-Publish ist ein
eigener Freigabe-Schritt des Owners.
