nanobot: 2026-09-14 21:12:30 — usage: skill + script fully English
This commit is contained in:
@@ -8,38 +8,49 @@ description: >
|
|||||||
|
|
||||||
# Usage
|
# Usage
|
||||||
|
|
||||||
Zobrazí spotřebu kreditů na Ollama Cloud pro aktuální API klíč.
|
Shows Ollama Cloud credit usage for the current API key.
|
||||||
|
|
||||||
## Spuštění
|
## Run
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
uv run skills/usage/scripts/ollama_usage.py
|
uv run skills/usage/scripts/ollama_usage.py
|
||||||
```
|
```
|
||||||
|
|
||||||
Skript čte `OLLAMA_API_KEY` z `workspace/.env` (vytvořeného uživatelem).
|
The script reads `OLLAMA_API_KEY` from the `workspace/.env` file (created by
|
||||||
Pokud chybí nebo klíč nefunguje (401/403), řekni to uživateli — nescrapuj web.
|
the user). If it is missing or the key fails (401/403), tell the user —
|
||||||
|
never scrape the website.
|
||||||
|
|
||||||
## Výstup
|
## Output
|
||||||
|
|
||||||
Text v češtině, přesně tento formát:
|
Format (script prints it, present it to the user as-is):
|
||||||
|
|
||||||
- `Session: <value> %, resets in X hours — <model> (<req count>), …`
|
```
|
||||||
- `Weekly: <value> %, resets in Y days — <model> (<req count>), …`
|
Ollama Cloud usage
|
||||||
- `Modely (počet požadavků, weekly okno):` — seznam modelů s requesty
|
Session: <pct> %, resets in X hours — <model> (<req count>), …
|
||||||
|
Weekly: <pct> %, resets in Y days — <model> (<req count>), …
|
||||||
|
Models (request count, weekly window):
|
||||||
|
<model>: <count>
|
||||||
|
```
|
||||||
|
|
||||||
## Reset časy — odvození, ne API
|
Present the script output to the user in Czech (translate the labels, keep
|
||||||
|
the numbers exact).
|
||||||
|
|
||||||
`/api/usage` **neobsahuje reset timestamps** (ty existují jen v HTML UI).
|
## Reset times — derived, not from the API
|
||||||
Skript je počítá: session = do další celé hodiny UTC (dashboard ukazuje
|
|
||||||
„Resets in 1 hour"), weekly = do nejbližšího pondělí 00:00 UTC.
|
|
||||||
Důvod: session usage šel v testu nahoru během pár minut (rolling okno),
|
|
||||||
weekly se mění pomalu, konzistentní s hodinovým/týdenním oknem.
|
|
||||||
Kdyby se ukázalo, že okno není kalendářové, uprav `until_next_*`.
|
|
||||||
|
|
||||||
## Poznámky
|
`/api/usage` contains **no reset timestamps** (they exist only in the HTML
|
||||||
|
UI). The script computes them: session = until the next full hour UTC (the
|
||||||
|
dashboard shows "Resets in 1 hour"), weekly = until the next Monday 00:00
|
||||||
|
UTC. Rationale: session usage climbed in real time during testing (rolling
|
||||||
|
window), weekly changes slowly — consistent with hourly/weekly windows.
|
||||||
|
If the window turns out not to be calendar-based, fix `until_next_*`.
|
||||||
|
|
||||||
- Endpoint: `GET https://ollama.com/api/usage`, hlavička
|
## Notes
|
||||||
`Authorization: Bearer <key>` (ověřeno 2026-09, issue #15132 je zastaralá).
|
|
||||||
- `limits.*.usage` je zlomek limitu plánu (× 100 = % jako na dashboardu).
|
- Endpoint: `GET https://ollama.com/api/usage`, header
|
||||||
- `activity.cost` u Pro plánu vrací $0.00000 — nefunkční, ve výstupu vynechán.
|
`Authorization: Bearer <key>` (verified 2026-09; issue #15132 is stale).
|
||||||
- Klíč z `~/.ollama/id_ed25519` nefunguje — jen API key z ollama.com.
|
- `limits.*.usage` is a fraction of the plan limit (× 100 = % as on the
|
||||||
|
dashboard).
|
||||||
|
- `activity.cost` returns $0.00000 on the Pro plan — broken, omitted from
|
||||||
|
the output.
|
||||||
|
- The `~/.ollama/id_ed25519` key does not work — only an API key minted at
|
||||||
|
ollama.com/settings/keys.
|
||||||
@@ -25,7 +25,7 @@ def load_api_key() -> str:
|
|||||||
line = line.strip()
|
line = line.strip()
|
||||||
if line.startswith("OLLAMA_API_KEY="):
|
if line.startswith("OLLAMA_API_KEY="):
|
||||||
return line.split("=", 1)[1].strip().strip('"').strip("'")
|
return line.split("=", 1)[1].strip().strip('"').strip("'")
|
||||||
sys.exit("OLLAMA_API_KEY nenalezen (ani env, ani workspace/.env)")
|
sys.exit("OLLAMA_API_KEY not found (neither env nor workspace/.env)")
|
||||||
|
|
||||||
|
|
||||||
def fmt_models(models: list[dict]) -> str:
|
def fmt_models(models: list[dict]) -> str:
|
||||||
@@ -54,8 +54,8 @@ def fmt_delta_short(td: timedelta) -> str:
|
|||||||
if total >= 86400:
|
if total >= 86400:
|
||||||
return f"{int(total // 86400)} days"
|
return f"{int(total // 86400)} days"
|
||||||
if total >= 3600:
|
if total >= 3600:
|
||||||
return f"{round(total / 3600)} hours"
|
return f"{round(td.total_seconds() / 3600)} hours"
|
||||||
return f"{max(1, round(total / 60))} minutes"
|
return f"{max(1, round(td.total_seconds() / 60))} minutes"
|
||||||
|
|
||||||
|
|
||||||
def main() -> None:
|
def main() -> None:
|
||||||
@@ -67,16 +67,16 @@ def main() -> None:
|
|||||||
with urllib.request.urlopen(req, timeout=15) as resp:
|
with urllib.request.urlopen(req, timeout=15) as resp:
|
||||||
data = json.load(resp)
|
data = json.load(resp)
|
||||||
except urllib.error.HTTPError as e:
|
except urllib.error.HTTPError as e:
|
||||||
sys.exit(f"ollama.com API chyba: HTTP {e.code}")
|
sys.exit(f"ollama.com API error: HTTP {e.code}")
|
||||||
except urllib.error.URLError as e:
|
except urllib.error.URLError as e:
|
||||||
sys.exit(f"ollama.com nedostupné: {e.reason}")
|
sys.exit(f"ollama.com unreachable: {e.reason}")
|
||||||
|
|
||||||
limits = data.get("limits", {})
|
limits = data.get("limits", {})
|
||||||
session = limits.get("session", {})
|
session = limits.get("session", {})
|
||||||
weekly = limits.get("weekly", {})
|
weekly = limits.get("weekly", {})
|
||||||
now = datetime.now(timezone.utc)
|
now = datetime.now(timezone.utc)
|
||||||
|
|
||||||
print("Ollama Cloud — spotřeba")
|
print("Ollama Cloud usage")
|
||||||
s_models = fmt_models(session.get("models", []))
|
s_models = fmt_models(session.get("models", []))
|
||||||
print(
|
print(
|
||||||
f'Session: {session.get("usage", 0) * 100:.1f} %, '
|
f'Session: {session.get("usage", 0) * 100:.1f} %, '
|
||||||
@@ -92,7 +92,7 @@ def main() -> None:
|
|||||||
|
|
||||||
models = weekly.get("models", [])
|
models = weekly.get("models", [])
|
||||||
if models:
|
if models:
|
||||||
print("Modely (počet požadavků, weekly okno):")
|
print("Models (request count, weekly window):")
|
||||||
for m in models:
|
for m in models:
|
||||||
print(f' {m["name"]}: {m["request_count"]}')
|
print(f' {m["name"]}: {m["request_count"]}')
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user