May 17, 2026, 11:40 PM
This commit is contained in:
@@ -0,0 +1,882 @@
|
||||
Pewnie — poniżej masz **dwie gotowe, “produkcyjne” wersje SKILL.md dopasowane pod OpenClaw runtime**:
|
||||
|
||||
1. **LLM‑only** (bez narzędzi)
|
||||
2. **Tool‑first** (narzędzia jako domyślny silnik, LLM tylko do planu/formatowania)
|
||||
|
||||
Dodatkowo dorzucam **gating (load-time)**, **slash-command**, oraz przykładowe **wpisy do `~/.openclaw/openclaw.json`** + rekomendowane **polityki narzędzi (`tools.profile/allow/deny`)**. Wszystko zgodne z tym, jak OpenClaw ładuje i filtruje skille. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/creating-skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
***
|
||||
|
||||
# 0) Kontekst OpenClaw (ważne, bo wpływa na projekt)
|
||||
|
||||
* Skill w OpenClaw to **katalog z plikiem `SKILL.md`** (YAML frontmatter + instrukcje w Markdown). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/creating-skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* Skille są ładowane m.in. z **`<workspace>/skills`** oraz **`~/.openclaw/skills`**; a gdy nazwy się pokrywają, **workspace wygrywa** nad lokalnym i bundlowanym. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* OpenClaw potrafi **filtrować skille przy ładowaniu** na podstawie `metadata.openclaw.requires` (np. wymagane binarki/env/config). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* Frontmatter ma ograniczenia: parser wspiera **jednolinijkowe klucze**, a `metadata` powinno być **jednolinijkowym JSON**. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* Dostępność i bezpieczeństwo narzędzi kontrolujesz w `openclaw.json` przez `tools.profile`, `tools.allow`, `tools.deny` i grupy `group:*`. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
***
|
||||
|
||||
# 1) Struktura katalogu (dla obu wariantów)
|
||||
|
||||
> Minimalnie:
|
||||
|
||||
<workspace>/skills/my-custom-skill-llm-only/SKILL.md
|
||||
<workspace>/skills/my-custom-skill-tool-first/SKILL.md
|
||||
|
||||
OpenClaw odkryje te katalogi i zindeksuje `SKILL.md` (po restarcie gateway albo “refresh skills”). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/creating-skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
***
|
||||
|
||||
# 2) Wersja A — **LLM‑only** (zero narzędzi, maksymalna przewidywalność)
|
||||
|
||||
### Kiedy to ma sens?
|
||||
|
||||
* gdy chcesz **czystą logikę/pisanie/transformację tekstu**
|
||||
* gdy chcesz **zero side‑effectów** i brak ryzyka tool‑abuse
|
||||
* gdy wolisz “prompt jako skill” + ustandaryzowany output
|
||||
|
||||
### `SKILL.md` (LLM‑only)
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-custom-skill-llm-only
|
||||
description: Deterministic LLM-only skill. No tools. Produces structured output for [topic].
|
||||
user-invocable: true
|
||||
disable-model-invocation: false
|
||||
metadata: {"openclaw":{"emoji":"🧠","os":["darwin","linux","win32"],"always":true}}
|
||||
---
|
||||
|
||||
# My Custom Skill (LLM-only)
|
||||
|
||||
## Purpose (single responsibility)
|
||||
Zamień nieuporządkowaną prośbę użytkownika na **ustrukturyzowaną odpowiedź** dla: **[topic]**.
|
||||
|
||||
## Hard rules (MUST)
|
||||
- **NIE używaj żadnych narzędzi** (read/write/exec/web_* / browser / nodes / cron).
|
||||
- Jeśli brakuje danych: **zadaj maksymalnie 3 pytania doprecyzowujące**.
|
||||
- Brak zgadywania faktów. Brak “dopowiadania” danych wejściowych.
|
||||
- Zachowaj deterministyczny format wyjścia (poniżej).
|
||||
|
||||
## When to use
|
||||
Użyj tylko gdy:
|
||||
- użytkownik chce: analizę/plan/porównanie/rewriting/checklistę/specyfikację dla **[topic]**
|
||||
Nie używaj gdy:
|
||||
- potrzebne jest pobranie danych z pliku/WWW/systemu albo jakiekolwiek działanie w środowisku.
|
||||
|
||||
## Output format (strict)
|
||||
Zwróć odpowiedź zawsze w tym układzie:
|
||||
|
||||
### TL;DR
|
||||
- ...
|
||||
|
||||
### Inputs (what I used)
|
||||
- ...
|
||||
|
||||
### Result
|
||||
- ...
|
||||
|
||||
### Assumptions
|
||||
- ...
|
||||
|
||||
### Next actions (max 5)
|
||||
1. ...
|
||||
2. ...
|
||||
|
||||
## Quality checklist (internal)
|
||||
- Czy output ma TL;DR + Inputs + Result + Assumptions + Next actions?
|
||||
- Czy nie ma w nim “narzędzi” ani sugestii wykonania poleceń?
|
||||
- Czy nie ma halucynacji faktów?
|
||||
```
|
||||
|
||||
**Dlaczego te pola?**
|
||||
|
||||
* `user-invocable` / `disable-model-invocation` to opcjonalne klucze frontmatter (OpenClaw) — przydatne do ekspozycji jako slash command albo ukrycia przed automatycznym doborem. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* `metadata` jako jednolinijkowy JSON i `always`/`os` są zgodne z mechanizmem gatingu. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
***
|
||||
|
||||
## Zalecana polityka narzędzi (żeby LLM‑only był naprawdę “no-tools”)
|
||||
|
||||
W `~/.openclaw/openclaw.json` ustaw np. profil minimalny (albo jawne deny):
|
||||
|
||||
```json5
|
||||
{
|
||||
"tools": {
|
||||
"profile": "minimal",
|
||||
"deny": ["group:fs", "group:runtime", "group:web", "group:ui", "group:nodes", "group:automation"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
* `tools.profile` i grupy `group:*` są wspierane i opisane w dokumentacji narzędzi. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
> Jeśli chcesz, możesz to ograniczyć per-agent (np. tylko dla “writer” agenta), ale powyższe jest najprostsze.
|
||||
|
||||
***
|
||||
|
||||
# 3) Wersja B — **Tool‑first** (narzędzia domyślnie, LLM tylko do planu + interpretacji)
|
||||
|
||||
### Kiedy to ma sens?
|
||||
|
||||
* gdy skill ma **pobierać dane** (pliki/WWW), **uruchamiać komendy**, **zapisywać artefakty**
|
||||
* gdy chcesz przewidywalny pipeline: preflight → gather → execute → output
|
||||
* gdy chcesz *mniej halucynacji*, bo fakty biorą się z tool outputów
|
||||
|
||||
***
|
||||
|
||||
## `SKILL.md` (Tool‑first)
|
||||
|
||||
> Uwaga: nazwy narzędzi i grupy są zgodne z listą OpenClaw tools (np. `read`, `write`, `exec`, `web_fetch`, `web_search`). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/web)
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-custom-skill-tool-first
|
||||
description: Tool-first skill for [topic]. Fetches/reads inputs, executes deterministic steps, writes auditable artifacts.
|
||||
user-invocable: true
|
||||
metadata: {"openclaw":{"emoji":"🛠️","requires":{"config":["tools.web.fetch.enabled"],"env":["MY_SKILL_API_KEY"],"bins":["jq"]},"primaryEnv":"MY_SKILL_API_KEY"}}
|
||||
---
|
||||
|
||||
# My Custom Skill (Tool-first)
|
||||
|
||||
## Purpose (single responsibility)
|
||||
Wykonaj workflow dla **[topic]** w sposób audytowalny:
|
||||
1) zbierz dane → 2) przetwórz → 3) zapisz wynik.
|
||||
|
||||
## Load-time gates (runtime safety)
|
||||
Ten skill ma być aktywny tylko gdy:
|
||||
- `MY_SKILL_API_KEY` jest dostępny (env lub skills.entries.*.apiKey),
|
||||
- `tools.web.fetch.enabled` jest włączone,
|
||||
- binarka `jq` istnieje na PATH.
|
||||
(Jeśli w sandboxie — binarka musi istnieć także w kontenerze.)
|
||||
|
||||
## Tools allowed (prefer)
|
||||
- `read` / `write` (artefakty)
|
||||
- `web_fetch` (zawartość stron)
|
||||
- `web_search` (tylko jeśli user nie podał URL)
|
||||
- `exec` (tylko deterministyczne polecenia, bez wstrzykiwania parametrów od usera)
|
||||
|
||||
## Guardrails (MUST)
|
||||
- Nie uruchamiaj `exec` z argumentami sklejanymi z surowego inputu użytkownika (ryzyko injection).
|
||||
- Zanim użyjesz narzędzi: wykonaj Pre-flight.
|
||||
- Zawsze zapisuj artefakty w `{baseDir}/runs/<timestamp>/...` (bezpieczny scope).
|
||||
- Jeśli jakikolwiek krok nie ma danych → przerwij i poproś o doprecyzowanie.
|
||||
|
||||
---
|
||||
|
||||
## Execution (deterministic)
|
||||
|
||||
### Step 0 — Pre-flight (fail-fast)
|
||||
1. Waliduj input (topic, opcje).
|
||||
2. Sprawdź dostępność narzędzi wymaganych w `requires`.
|
||||
3. Ustaw `runId = YYYYMMDD-HHMMSS` i katalog:
|
||||
`{baseDir}/runs/{runId}/`
|
||||
|
||||
### Step 1 — Gather (minimum necessary)
|
||||
- Jeśli user podał URL → `web_fetch(url=...)`
|
||||
- Jeśli nie podał URL → `web_search(query=...)` → wybierz 1–3 wyniki → `web_fetch(...)`
|
||||
- Jeśli user podał plik ścieżką → `read(path=...)`
|
||||
|
||||
Zapisz:
|
||||
- `{baseDir}/runs/{runId}/inputs.json`
|
||||
- `{baseDir}/runs/{runId}/sources.md`
|
||||
|
||||
### Step 2 — Transform (tool-first)
|
||||
- Preferuj deterministyczne przetwarzanie:
|
||||
- proste ekstrakcje i walidacje przez `exec` (np. `jq`) tylko na danych z własnych plików w katalogu run.
|
||||
- LLM używaj tylko do:
|
||||
- ułożenia planu
|
||||
- formatowania końcowego raportu
|
||||
|
||||
Zapisz:
|
||||
- `{baseDir}/runs/{runId}/result.raw`
|
||||
|
||||
### Step 3 — Output (auditable)
|
||||
Wygeneruj raport w Markdown:
|
||||
- `{baseDir}/runs/{runId}/report.md`
|
||||
|
||||
Raport MA zawierać:
|
||||
- TL;DR
|
||||
- Źródła (linki/fragmenty)
|
||||
- Kroki wykonania (logicznie, bez sekretów)
|
||||
- Artefakty (ścieżki)
|
||||
|
||||
Na końcu zwróć użytkownikowi:
|
||||
- krótką odpowiedź + link/ścieżkę do report.md
|
||||
```
|
||||
|
||||
### Dlaczego takie `metadata.openclaw.requires`?
|
||||
|
||||
* `requires.bins/env/config` to dokładnie ten mechanizm, którym OpenClaw filtruje skille przy ładowaniu. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* `primaryEnv` wiąże się z wygodnym `skills.entries.<name>.apiKey` w configu. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* `{baseDir}` to wspierany placeholder do referencji folderu skilla. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
***
|
||||
|
||||
## Zalecana konfiguracja `skills.entries` (openclaw\.json)
|
||||
|
||||
```json5
|
||||
{
|
||||
"skills": {
|
||||
"entries": {
|
||||
"my-custom-skill-tool-first": {
|
||||
"enabled": true,
|
||||
"apiKey": { "source": "env", "provider": "default", "id": "MY_SKILL_API_KEY" },
|
||||
"env": {
|
||||
"MY_SKILL_API_KEY": "REDACTED"
|
||||
},
|
||||
"config": {
|
||||
"maxRetries": 2,
|
||||
"maxSources": 3
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
* `skills.entries.*.env`, `skills.entries.*.apiKey` i `skills.entries.*.config` są wspierane jako override per-skill. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
***
|
||||
|
||||
## Zalecana polityka narzędzi dla Tool‑first (żeby działał i był bezpieczny)
|
||||
|
||||
```json5
|
||||
{
|
||||
"tools": {
|
||||
"profile": "coding",
|
||||
"allow": ["group:fs", "group:web", "group:runtime"],
|
||||
"deny": ["browser", "canvas", "nodes", "cron"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
* Profile (`coding`) i grupy (`group:fs`, `group:web`, `group:runtime`) są częścią mechanizmu policy w OpenClaw. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
* `web_fetch` i `web_search` to wbudowane web narzędzia (bez JS; do JS‑heavy stron jest `browser`). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/web), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
***
|
||||
|
||||
# 4) Bonus: “hybryda” sterowana komendą (szybki slash → tool dispatch)
|
||||
|
||||
Jeśli chcesz, żeby komenda **omijała model** i wywoływała bezpośrednio narzędzie (np. do “/my-skill fetch …”), możesz użyć `command-dispatch: tool` + `command-tool`.
|
||||
To jest super do operacji typu “zrób X jednym tool‑call”. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
***
|
||||
|
||||
# 5) Dwa krótkie wybory architektoniczne (żebyś nie wpadł w typowe pułapki)
|
||||
|
||||
### LLM‑only
|
||||
|
||||
✅ przewidywalne, zero side‑effectów, tanie w utrzymaniu
|
||||
❌ nie pobierze danych z zewnątrz, nie zapisze plików (chyba że pozwolisz narzędzia)
|
||||
|
||||
### Tool‑first
|
||||
|
||||
✅ minimalizuje halucynacje, audytowalne artefakty, pipeline “jak w produkcji”
|
||||
❌ wymaga dobrych guardrails i policy (szczególnie dla `exec`) [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
***
|
||||
|
||||
## Pytanie, które pozwoli mi dopiąć to “na gotowo” (bez długiej wymiany)
|
||||
|
||||
Jaki jest **konkretny cel** Twojego skilla w praktyce?
|
||||
|
||||
Daj 1 zdanie w stylu:
|
||||
|
||||
* “Zbiera dane z URL + robi raport”
|
||||
* “Czyta logi / pliki i generuje podsumowanie”
|
||||
* “Uruchamia komendy diagnostyczne (DB/Splunk/SQL) i zapisuje wynik”
|
||||
|
||||
…i wtedy dopasuję Ci:
|
||||
|
||||
* dokładne `requires.config` pod Twoje narzędzia,
|
||||
* strukturę artefaktów,
|
||||
* i bezpieczne allowlisty dla `exec` (jeśli w ogóle ma być).
|
||||
|
||||
|
||||
Jasne — poniżej masz **wersję hybrydową SKILL.md dla OpenClaw**, która łączy:
|
||||
|
||||
1. **tryb “agentowy” (LLM + tool‑first)** w normalnej rozmowie
|
||||
2. **tryb “komendowy” (/… → direct tool dispatch)** dla deterministycznych akcji ze slash command
|
||||
|
||||
To jest zgodne z tym, jak OpenClaw ładuje skille z katalogu z `SKILL.md` (YAML frontmatter + Markdown) i jak działa gating (`metadata.openclaw.requires`) oraz obsługa slash commands (`user-invocable`, `command-dispatch`, `command-tool`, `command-arg-mode`). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/creating-skills), [\[moely.ai\]](https://www.moely.ai/resources/openclaw-skills-extension-design)
|
||||
|
||||
> **Uwaga praktyczna:** Direct tool dispatch wymaga, żeby wskazany tool akceptował parametry przekazywane przez dispatcher (`{ command, commandName, skillName }`). OpenClaw opisuje to wprost.
|
||||
> Jeśli Twoja instalacja ma **ściśle walidowane schematy narzędzi** i wywali się na “nadmiarowych polach”, daję też wariant “bez bypassu” (slash dalej wybiera skill, ale przez LLM) w sekcji **Plan B**. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[moely.ai\]](https://www.moely.ai/resources/openclaw-skills-extension-design)
|
||||
|
||||
***
|
||||
|
||||
## ✅ 1) Hybrydowy `SKILL.md` (Tool‑first + Slash direct-dispatch)
|
||||
|
||||
Wklej jako:
|
||||
`<workspace>/skills/my-custom-skill-hybrid/SKILL.md`
|
||||
(Workspace ma najwyższy priorytet ładowania względem `~/.openclaw/skills` i bundli). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/creating-skills)
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-custom-skill-hybrid
|
||||
description: Hybrid skill: tool-first in chat, optional deterministic slash dispatch (bypass model) for quick actions.
|
||||
user-invocable: true
|
||||
disable-model-invocation: false
|
||||
command-dispatch: tool
|
||||
command-tool: exec
|
||||
command-arg-mode: raw
|
||||
metadata: {"openclaw":{"emoji":"🧩","os":["darwin","linux","win32"],"requires":{"config":["tools.exec.enabled"],"bins":["jq"]}}}
|
||||
---
|
||||
|
||||
# My Custom Skill (HYBRID)
|
||||
|
||||
Ten skill ma **dwa tryby pracy**:
|
||||
|
||||
## Mode A — Chat / Agent mode (default)
|
||||
Gdy użytkownik opisuje problem normalnie, skill działa **tool-first**:
|
||||
- zbierz dane (read/web_fetch/web_search)
|
||||
- przetwórz deterministycznie (preferuj narzędzia)
|
||||
- dopiero na końcu użyj LLM do formatowania raportu
|
||||
|
||||
## Mode B — Slash / Deterministic mode (bypass model)
|
||||
Gdy użytkownik użyje komendy slash dla tego skilla, OpenClaw ma **ominiąć model**
|
||||
i wywołać wskazane narzędzie bezpośrednio (command-dispatch: tool).
|
||||
W tym trybie parametr `args` trafia jako `command` do toola.
|
||||
|
||||
> Komenda jest przekazywana jako:
|
||||
> { command: "<raw args>", commandName: "<slash>", skillName: "<skill>" }.
|
||||
|
||||
---
|
||||
|
||||
## Safety & Guardrails (MANDATORY)
|
||||
- Nigdy nie wykonuj poleceń destrukcyjnych (rm -rf, format, wipe, itp.).
|
||||
- Nie uruchamiaj poleceń z sekretami w treści.
|
||||
- Jeśli w Mode A potrzebujesz `exec`, to:
|
||||
- używaj allowlisty komend,
|
||||
- nie sklejaj argumentów z “surowego” inputu użytkownika.
|
||||
- Artefakty zapisuj wyłącznie w `{baseDir}/runs/<runId>/`.
|
||||
|
||||
---
|
||||
|
||||
## When to Use
|
||||
Użyj, gdy użytkownik chce:
|
||||
- zebrać dane z pliku/URL i zrobić raport / analizę dla [topic]
|
||||
- albo wykonać szybkie, deterministyczne akcje komendą (Mode B)
|
||||
|
||||
Nie używaj, gdy:
|
||||
- zadanie wymaga browser logowania/JS-heavy — wtedy preferuj browser tool (poza tym skillem).
|
||||
|
||||
---
|
||||
|
||||
## Execution (Mode A — tool-first)
|
||||
|
||||
### Step 0: Pre-flight
|
||||
1) Ustal `runId = YYYYMMDD-HHMMSS`.
|
||||
2) Sprawdź, czy masz minimalne dane wejściowe (topic / źródło / zakres).
|
||||
3) Jeśli braki → max 3 pytania doprecyzowujące.
|
||||
|
||||
### Step 1: Gather
|
||||
- Jeśli user podał plik → `read`
|
||||
- Jeśli podał URL → `web_fetch`
|
||||
- Jeśli nie podał źródła → `web_search` (max 3 wyniki) → `web_fetch`
|
||||
|
||||
Zapisz:
|
||||
- `{baseDir}/runs/{runId}/inputs.json`
|
||||
- `{baseDir}/runs/{runId}/sources.md`
|
||||
|
||||
### Step 2: Transform
|
||||
- Preferuj narzędzia i deterministykę.
|
||||
- Jeśli musisz, użyj `exec` tylko dla bezpiecznych transformacji na plikach z katalogu run.
|
||||
- LLM wyłącznie do: streszczenia, formatowania, wyjaśnienia.
|
||||
|
||||
Zapisz:
|
||||
- `{baseDir}/runs/{runId}/result.raw`
|
||||
|
||||
### Step 3: Output
|
||||
Wygeneruj `{baseDir}/runs/{runId}/report.md` zawierający:
|
||||
- TL;DR
|
||||
- Źródła i cytowane fragmenty
|
||||
- Kroki wykonania (bez sekretów)
|
||||
- Artefakty (ścieżki)
|
||||
|
||||
---
|
||||
|
||||
## Slash usage (Mode B — bypass model)
|
||||
|
||||
### /my-custom-skill-hybrid <raw>
|
||||
Przykłady (bezpieczne, read-only):
|
||||
- `/my-custom-skill-hybrid echo "hello"`
|
||||
- `/my-custom-skill-hybrid jq --version`
|
||||
|
||||
Zasady:
|
||||
- traktuj to jako tryb “operator executes a command”
|
||||
- jeśli komenda wygląda na destrukcyjną → przerwij i poproś o potwierdzenie poza trybem bypass
|
||||
```
|
||||
|
||||
### Dlaczego to jest “OpenClaw‑native”?
|
||||
|
||||
* Skill jako katalog z `SKILL.md` + frontmatter jest standardem OpenClaw. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/creating-skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* `metadata.openclaw.requires` (bins/config/os) to mechanizm **load‑time gating**. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[moely.ai\]](https://www.moely.ai/resources/openclaw-skills-extension-design)
|
||||
* `user-invocable`, `command-dispatch: tool`, `command-tool`, `command-arg-mode` to oficjalnie opisane pola dla komend i bypassu. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[moely.ai\]](https://www.moely.ai/resources/openclaw-skills-extension-design)
|
||||
* `exec` jest narzędziem do uruchamiania komend, kontrolowanym politykami narzędzi. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
***
|
||||
|
||||
## ✅ 2) Konfiguracja `openclaw.json` (narzędzia + skill entry)
|
||||
|
||||
### a) Bezpieczna polityka narzędzi (dla hybrydy)
|
||||
|
||||
Poniżej ustawiasz profil i allow/deny (OpenClaw wspiera `tools.profile`, `tools.allow`, `tools.deny` i grupy). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
```json5
|
||||
{
|
||||
"tools": {
|
||||
"profile": "coding",
|
||||
"allow": ["group:fs", "group:web", "group:runtime"],
|
||||
"deny": ["browser", "canvas", "nodes", "cron"]
|
||||
},
|
||||
"skills": {
|
||||
"entries": {
|
||||
"my-custom-skill-hybrid": {
|
||||
"enabled": true,
|
||||
"config": {
|
||||
"maxSources": 3,
|
||||
"maxRetries": 2
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
***
|
||||
|
||||
# 🔧 Plan B (jeśli direct-dispatch nie działa w Twojej instalacji)
|
||||
|
||||
W części wdrożeń bywa, że komendy skillowe (w tym `command-dispatch: tool`) nie odpalają się jak trzeba zależnie od wersji/konfiguracji (widziano przypadek zależności od aliasów modeli). [\[github.com\]](https://github.com/openclaw/openclaw/issues/25239)
|
||||
|
||||
**Wtedy zrób hybrydę bez bypassu:**
|
||||
|
||||
* Usuń z frontmatter:
|
||||
* `command-dispatch`, `command-tool`, `command-arg-mode`
|
||||
* Zostaw `user-invocable: true`
|
||||
* A w treści skilla dodaj regułę:
|
||||
* “Jeśli użytkownik wywoła skill ze slash command i poda argumenty, traktuj je jako ‘tryb komendowy’, ale nadal przejdź przez Pre-flight i guardrails.”
|
||||
|
||||
To nadal daje **dwa tryby**, tylko Mode B idzie przez LLM (mniej deterministycznie, ale bardziej kompatybilnie). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
***
|
||||
|
||||
# Następny krok (żeby to było “idealnie pod Ciebie”)
|
||||
|
||||
W tej chwili hybryda ma Mode B ustawiony na `exec` (bo to najprostszy “tool dispatch”).
|
||||
Powiedz mi w 1 zdaniu: **co Mode B ma robić w Twoim realnym use-case?** [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
Przykłady:
|
||||
|
||||
* “/skill diag” → zebrać statusy i zapisać report
|
||||
* “/skill fetch <url>” → pobrać stronę i znormalizować do markdown
|
||||
* “/skill sqlcheck” → odpalić kilka read-only poleceń diagnostycznych
|
||||
|
||||
A ja dopasuję:
|
||||
|
||||
* bezpieczną allowlistę komend (albo całkiem wyeliminuję `exec`),
|
||||
* parametry “raw args” i format,
|
||||
* oraz gating (`requires.config/env/bins`) pod Twoje runtime. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools)
|
||||
|
||||
|
||||
Pewnie — pokażę Ci **jak wygląda rozbicie na “skill (orchestrator) + sub‑skille” w OpenClaw** oraz dorzucę **allowlistę komend** (dla `exec`) tak, żeby dało się to utrzymać i nie otworzyć sobie drzwi na command‑injection. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model), [\[deepwiki.com\]](https://deepwiki.com/openclaw/openclaw/6.4-skills-system)
|
||||
|
||||
> **Ważna uwaga o architekturze w OpenClaw:** “sub‑skille” to po prostu **osobne skille** (oddzielne katalogi z `SKILL.md`), które agent wybiera zależnie od intencji. Orchestrator nie “wywołuje” ich jak funkcji w kodzie, ale **kieruje agentem** (instrukcjami) żeby użył właściwego sub-skilla dla danego kroku. OpenClaw ładuje i filtruje skille (gating), a potem wstrzykuje ich opis do promptu, na podstawie którego model decyduje, którego użyć. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[deepwiki.com\]](https://deepwiki.com/openclaw/openclaw/6.4-skills-system)
|
||||
|
||||
***
|
||||
|
||||
## 1) Jak to będzie wyglądać — struktura katalogów (suite: skill + sub‑skille)
|
||||
|
||||
Skille w OpenClaw to **katalog + `SKILL.md`**; najlepiej trzymać to w `<workspace>/skills`, bo ma najwyższy priorytet nad `~/.openclaw/skills` i bundlami. [\[deepwiki.com\]](https://deepwiki.com/openclaw/openclaw/6.4-skills-system), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
Przykładowa “paczka” (suite):
|
||||
|
||||
<workspace>/skills/
|
||||
my-suite-orchestrator/
|
||||
SKILL.md
|
||||
my-suite-gather-web/
|
||||
SKILL.md
|
||||
my-suite-gather-files/
|
||||
SKILL.md
|
||||
my-suite-transform/
|
||||
SKILL.md
|
||||
my-suite-report/
|
||||
SKILL.md
|
||||
my-suite-quickfetch/ # opcjonalny "hybrydowy" slash bypass (bezpieczny)
|
||||
SKILL.md
|
||||
|
||||
* **orchestrator**: routuje do sub-skilli + trzyma wspólne guardrails i spójny format artefaktów. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* **gather-\***: izolują pobieranie danych (WWW / pliki). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model), [\[deepwiki.com\]](https://deepwiki.com/miaoxworld/OpenClawInstaller/5.3-creating-custom-skills)
|
||||
* **transform**: deterministyczne przetwarzanie + allowlista `exec`. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* **report**: format i finalny raport. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
* **quickfetch**: jeśli chcesz **prawdziwy “hybrydowy” bypass** bez ryzyka (dispatch do `web_fetch`, a nie do `exec`). `web_fetch` jest z natury “bezpieczniejszy” niż `exec`, bo nie uruchamia poleceń, tylko pobiera URL i ekstrahuje treść. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model), [\[deepwiki.com\]](https://deepwiki.com/miaoxworld/OpenClawInstaller/5.3-creating-custom-skills)
|
||||
|
||||
***
|
||||
|
||||
## 2) Skill #1 — Orchestrator (główny “suite skill”)
|
||||
|
||||
**Cel:** jeden skill, który:
|
||||
|
||||
* wybiera odpowiedni sub-skill,
|
||||
* pilnuje spójnej struktury `runs/<runId>/`,
|
||||
* pilnuje zasad bezpieczeństwa i “kiedy exec jest w ogóle dozwolony”. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
`<workspace>/skills/my-suite-orchestrator/SKILL.md`
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-suite-orchestrator
|
||||
description: Orchestrates the suite: routes to sub-skills, enforces guardrails, and produces auditable outputs.
|
||||
user-invocable: true
|
||||
metadata: {"openclaw":{"emoji":"🧭","always":true}}
|
||||
---
|
||||
|
||||
# My Suite — Orchestrator
|
||||
|
||||
## Responsibility (single)
|
||||
Zarządzaj wykonaniem zadania: wybierz właściwy sub-skill, utrzymaj porządek artefaktów i guardrails.
|
||||
|
||||
## Routing rules (deterministic)
|
||||
- Jeśli źródło to URL / WWW → użyj **my-suite-gather-web**
|
||||
- Jeśli źródło to plik/ścieżka → użyj **my-suite-gather-files**
|
||||
- Jeśli trzeba przetworzyć/oczyścić dane → użyj **my-suite-transform**
|
||||
- Jeśli trzeba złożyć wynik w raport → użyj **my-suite-report**
|
||||
|
||||
## Global guardrails (MUST)
|
||||
- Preferuj narzędzia “read-only” i web tools (web_fetch/web_search) nad exec.
|
||||
- `exec` tylko gdy:
|
||||
1) to konieczne,
|
||||
2) pasuje do allowlisty z my-suite-transform,
|
||||
3) dotyczy wyłącznie plików w `{baseDir}/runs/<runId>/`.
|
||||
- Artefakty zapisuj w `{baseDir}/runs/<runId>/...`
|
||||
- Jeśli brakuje danych → max 3 pytania doprecyzowujące, potem stop.
|
||||
|
||||
## Output contract
|
||||
Zawsze zwróć:
|
||||
- TL;DR
|
||||
- Co było wejściem
|
||||
- Co powstało (artefakty i ścieżki)
|
||||
- Następne kroki
|
||||
```
|
||||
|
||||
**Dlaczego tak?** Orchestrator wykorzystuje fakt, że OpenClaw “podaje” modelowi listę dostępnych skilli i narzędzi, więc routing robimy instrukcjami (deterministycznie). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 3) Sub-skill: Gather Web (web\_search + web\_fetch)
|
||||
|
||||
`<workspace>/skills/my-suite-gather-web/SKILL.md`
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-suite-gather-web
|
||||
description: Fetches sources from the web. Uses web_search when needed, then web_fetch for extraction.
|
||||
user-invocable: false
|
||||
metadata: {"openclaw":{"emoji":"🌐","requires":{"config":["tools.web.fetch.enabled"]}}}
|
||||
---
|
||||
|
||||
# Gather Web
|
||||
|
||||
## When to use
|
||||
- Użytkownik podał URL lub trzeba znaleźć źródła w WWW.
|
||||
|
||||
## Steps
|
||||
1) Jeśli jest URL → `web_fetch(url=..., extractMode="markdown")`
|
||||
2) Jeśli brak URL → `web_search(query=..., count=3)` → wybierz 1–3 wyniki → `web_fetch(...)`
|
||||
|
||||
## Artifacts
|
||||
Zapisz do:
|
||||
- `{baseDir}/runs/<runId>/sources.md` (linki + krótkie ekstrakty)
|
||||
- `{baseDir}/runs/<runId>/inputs.json` (metadane wejścia)
|
||||
```
|
||||
|
||||
`web_search` i `web_fetch` są oficjalnymi web toolami w OpenClaw (wyszukiwanie + fetch bez JS). [\[deepwiki.com\]](https://deepwiki.com/miaoxworld/OpenClawInstaller/5.3-creating-custom-skills), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 4) Sub-skill: Gather Files (read)
|
||||
|
||||
`<workspace>/skills/my-suite-gather-files/SKILL.md`
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-suite-gather-files
|
||||
description: Loads input from local files safely and stores normalized copies in the run folder.
|
||||
user-invocable: false
|
||||
metadata: {"openclaw":{"emoji":"📁","requires":{"config":["group:fs"]}}}
|
||||
---
|
||||
|
||||
# Gather Files
|
||||
|
||||
## When to use
|
||||
- Użytkownik wskazuje plik/ścieżkę lub potrzebujesz odczytać artefakt z wcześniejszego run.
|
||||
|
||||
## Steps
|
||||
1) Użyj `read(path=...)` na wejściu.
|
||||
2) Skopiuj/znormalizuj treść do `{baseDir}/runs/<runId>/input.txt` (bez modyfikowania oryginału).
|
||||
|
||||
## Artifacts
|
||||
- `{baseDir}/runs/<runId>/input.txt`
|
||||
- `{baseDir}/runs/<runId>/inputs.json`
|
||||
```
|
||||
|
||||
Narzędzia plikowe (`read/write/edit/...`) są grupowane i kontrolowane politykami tooli w OpenClaw (`group:fs`). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 5) Sub-skill: Transform (TU dodajemy allowlistę komend)
|
||||
|
||||
To jest miejsce, gdzie robisz “bezpieczny runtime” dla `exec`. `exec` w OpenClaw to narzędzie do uruchamiania komend w workspace (z parametrami m.in. `command`, `timeout`, `security`). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
`<workspace>/skills/my-suite-transform/SKILL.md`
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-suite-transform
|
||||
description: Deterministic transformations with a strict command allowlist (exec is optional and constrained).
|
||||
user-invocable: false
|
||||
metadata: {"openclaw":{"emoji":"🧪","requires":{"config":["group:runtime"],"bins":["jq"]}}}
|
||||
---
|
||||
|
||||
# Transform (Allowlisted exec)
|
||||
|
||||
## Golden rule
|
||||
Preferuj transformacje bez `exec`. Jeśli `exec` jest potrzebny → tylko allowlista poniżej.
|
||||
|
||||
## Command allowlist (STRICT)
|
||||
Dozwolone są WYŁĄCZNIE te komendy (dokładne wzorce):
|
||||
|
||||
1) `jq --version`
|
||||
2) `jq -c . <INPUT >OUTPUT`
|
||||
3) `jq -r . <INPUT >OUTPUT`
|
||||
4) `head -n <N> <INPUT`
|
||||
5) `tail -n <N> <INPUT`
|
||||
6) `wc -l <INPUT`
|
||||
7) `grep -n "<literal>" <INPUT`
|
||||
8) `sed -n '<start>,<end>p' <INPUT`
|
||||
|
||||
### Constraints (MUST)
|
||||
- `<INPUT>` i `<OUTPUT>` MUSZĄ być ścieżkami pod `{baseDir}/runs/<runId>/`
|
||||
- `<N>` to liczba 1..500
|
||||
- `"<literal>"` nie może zawierać znaków: `; | & $ \` ( ) { }`
|
||||
- Zakaz: `rm`, `mv`, `cp` poza run, `curl`, `wget`, `ssh`, `sudo`, `chmod`, `chown`, `dd`, `mkfs`, `> /dev/*` itd.
|
||||
|
||||
## Execution steps
|
||||
1) Waliduj, czy polecenie pasuje do allowlisty i constraintów.
|
||||
2) Jeśli nie pasuje → przerwij i zaproponuj alternatywę bez exec.
|
||||
3) Jeśli pasuje → uruchom `exec` tylko na plikach w katalogu run.
|
||||
4) Wynik zapisz do:
|
||||
- `{baseDir}/runs/<runId>/transform.log`
|
||||
- `{baseDir}/runs/<runId>/<output files>`
|
||||
|
||||
## Why this exists
|
||||
Zapobiega command injection i ogranicza skutki błędów do sandboxowego katalogu run.
|
||||
```
|
||||
|
||||
### Dlaczego allowlista w SKILL.md ma sens?
|
||||
|
||||
Bo w OpenClaw to model wybiera i parametryzuje tool‑call (np. `exec(command=...)`), a Ty chcesz mu **zawęzić przestrzeń decyzji** do znanych, bezpiecznych wzorców. Narzędzie `exec` jest potężne, więc guardrails muszą być twarde. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 6) Sub-skill: Report (formatowanie i final)
|
||||
|
||||
`<workspace>/skills/my-suite-report/SKILL.md`
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-suite-report
|
||||
description: Produces the final report.md from gathered/transformed artifacts. No exec.
|
||||
user-invocable: false
|
||||
metadata: {"openclaw":{"emoji":"📝","always":true}}
|
||||
---
|
||||
|
||||
# Report
|
||||
|
||||
## Inputs
|
||||
- `{baseDir}/runs/<runId>/sources.md` i/lub `input.txt`
|
||||
- `{baseDir}/runs/<runId>/result.raw` (jeśli istnieje)
|
||||
- `transform.log` (opcjonalnie)
|
||||
|
||||
## Output
|
||||
Zapisz:
|
||||
- `{baseDir}/runs/<runId>/report.md`
|
||||
|
||||
Format report.md:
|
||||
- TL;DR
|
||||
- Evidence (źródła, linki, fragmenty)
|
||||
- Steps taken (bez sekretów)
|
||||
- Artifacts (ścieżki)
|
||||
- Next actions (max 5)
|
||||
```
|
||||
|
||||
***
|
||||
|
||||
## 7) Hybryda: “quick” slash bypass (bezpieczny) — opcjonalnie 📦
|
||||
|
||||
Jeśli nadal chcesz “hybrydę” w sensie **slash command → direct tool dispatch**, to **nie dispatchuj do `exec`** (bo omijasz model, więc omijasz allowlistę!). Zamiast tego zrób osobny “quickfetch” dispatchujący do `web_fetch`. Mechanizm `command-dispatch: tool` + `command-tool` jest wspierany. [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
`<workspace>/skills/my-suite-quickfetch/SKILL.md`
|
||||
|
||||
```markdown
|
||||
---
|
||||
name: my-suite-quickfetch
|
||||
description: Slash-safe quick fetch: bypass model and run web_fetch directly on provided URL.
|
||||
user-invocable: true
|
||||
command-dispatch: tool
|
||||
command-tool: web_fetch
|
||||
command-arg-mode: raw
|
||||
metadata: {"openclaw":{"emoji":"⚡","requires":{"config":["tools.web.fetch.enabled"]}}}
|
||||
---
|
||||
|
||||
# QuickFetch (slash)
|
||||
|
||||
Usage:
|
||||
- `/my-suite-quickfetch https://example.com`
|
||||
|
||||
Notes:
|
||||
- This bypasses the model and dispatches to web_fetch.
|
||||
- Provide a single URL as the raw args string.
|
||||
```
|
||||
|
||||
`web_fetch` jest narzędziem do pobrania i ekstrakcji treści (bez JS), więc jako bypass jest dużo mniej ryzykowne niż `exec`. [\[deepwiki.com\]](https://deepwiki.com/miaoxworld/OpenClawInstaller/5.3-creating-custom-skills), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
# 8) Konfiguracja narzędzi (tools policy) — minimalny “safe” zestaw
|
||||
|
||||
OpenClaw pozwala ustawić bazową politykę przez `tools.profile` oraz `tools.allow/deny` i grupy (`group:fs`, `group:web`, `group:runtime`). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
Przykład “suite-friendly” (umożliwia pliki+web+exec, ale blokuje UI/nodes/cron):
|
||||
|
||||
```json5
|
||||
{
|
||||
"tools": {
|
||||
"profile": "coding",
|
||||
"allow": ["group:fs", "group:web", "group:runtime"],
|
||||
"deny": ["browser", "canvas", "nodes", "cron"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
***
|
||||
|
||||
# 9) Co dostajesz dzięki takiemu rozbiciu?
|
||||
|
||||
✅ **Mniej halucynacji** (gather i transform to narzędzia, a nie “zgadywanie”).
|
||||
✅ **Mniejszy prompt** per skill (sub‑skille są węższe i prostsze).
|
||||
✅ **Łatwiejszy audyt** (artefakty w jednym run folderze).
|
||||
✅ **Bezpieczniejsze `exec`** dzięki allowliście + constraintom na ścieżki.
|
||||
✅ **“Hybryda”**: szybki slash do bezpiecznego toola (`web_fetch`) + pełny agentowy pipeline w rozmowie. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model), [\[deepwiki.com\]](https://deepwiki.com/miaoxworld/OpenClawInstaller/5.3-creating-custom-skills) [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills) [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model) [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model) [\[deepwiki.com\]](https://deepwiki.com/miaoxworld/OpenClawInstaller/5.3-creating-custom-skills), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## Szybkie doprecyzowanie (jedno zdanie wystarczy)
|
||||
|
||||
Chcesz allowlistę komend pod **jakie realne zadania**? (np. parsowanie JSON logów, wyciąganie fragmentów tekstu, walidacja plików, itd.)
|
||||
|
||||
Jeśli powiesz “do czego”, dopasuję allowlistę tak, żeby:
|
||||
|
||||
* była **minimalna** (im mniej, tym lepiej),
|
||||
* nie była “zbyt ogólna” (np. nie dam `python -c` bo to prawie jak pełny shell),
|
||||
* i żeby nie blokowała Twojego flow.
|
||||
|
||||
Poniżej masz **praktyczne ograniczenia i “pułapki” używania `exec` w OpenClaw** – czyli co realnie ogranicza to narzędzie, jak działa w sandboxie/na hoście, jakie ma limity i jakie mechanizmy bezpieczeństwa wpływają na to, czy komenda w ogóle się wykona. Wszystko w oparciu o oficjalny opis narzędzi OpenClaw. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 1) `exec` działa w określonym “kontekście uruchomienia” (workspace / sandbox / node)
|
||||
|
||||
* Domyślnie `exec` uruchamia komendy **w workspace** (w praktyce: w katalogu roboczym sesji/agenta). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* `exec` ma parametr `host`, który determinuje **gdzie** wykonać polecenie: `sandbox | gateway | node`. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* W trybie sandbox (kontener) to, co działa na hoście, **nie musi działać w sandboxie** (brak binarek, brak sieci, inny filesystem). OpenClaw wprost zaznacza, że przy sandboxie binarki wymagane przez skill muszą istnieć również w kontenerze, a instalacje w kontenerze wymagają m.in. egressu sieci, zapisywalnego FS i uprawnień (root). [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
**Wniosek:** jeśli Twoja komenda “działa u Ciebie w terminalu”, to nadal może nie działać w sandboxie agenta (inne środowisko). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model), [\[docs.openclaw.ai\]](https://docs.openclaw.ai/tools/skills)
|
||||
|
||||
***
|
||||
|
||||
## 2) Narzędzie może być całkowicie niedostępne przez polityki narzędzi (`tools.profile/allow/deny`)
|
||||
|
||||
* OpenClaw ma globalne polityki narzędzi: `tools.profile`, `tools.allow`, `tools.deny` (deny wygrywa) i wspiera grupy typu `group:runtime` (gdzie jest m.in. `exec`). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* Jeśli `exec` (albo `group:runtime`) jest zablokowany w polityce, to model **nie dostanie** schematu narzędzia, a więc nie będzie mógł go wywołać. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
**Wniosek:** “skill mówi żeby użyć exec” ≠ “agent może użyć exec”. O tym decyduje policy. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 3) `exec` ma wbudowane limity czasu i tryby pracy (sync vs background)
|
||||
|
||||
* Kluczowe parametry `exec` to m.in.: `yieldMs` (domyślnie 10000), `background`, `timeout` (sekundy; domyślnie 1800), `pty`, `host`, `security`, `ask`. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* Jeśli proces przekroczy `yieldMs`, OpenClaw może go **zabackgroundować** i zwrócić status `running` z `sessionId`. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* Do obsługi procesów w tle służy narzędzie `process` (list/poll/log/write/kill/clear/remove). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* Jeżeli `process` jest zablokowane, OpenClaw zaznacza, że `exec` działa wtedy **synchronicznie** i ignoruje `yieldMs/background` (czyli tracisz wygodny mechanizm long‑running jobów). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
**Wniosek:** długie komendy bez `process` mogą “nie mieć gdzie żyć” – albo będą ucinane/timeoutowane, albo zablokują przebieg. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 4) Ograniczenia bezpieczeństwa: `security` + “exec approvals” + `ask`
|
||||
|
||||
OpenClaw przewiduje kilka warstw kontroli:
|
||||
|
||||
* `exec` ma parametr `security` (np. `deny | allowlist | full`) i parametr `ask` (`off | on-miss | always`) do sterowania zgodami/warunkami uruchomienia. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* Dodatkowo, OpenClaw ma osobny mechanizm “Exec approvals” (zatwierdzanie/ograniczanie uruchamiania komend) – dokumentacja `exec` odwołuje się do tego wprost. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* W praktyce oznacza to, że nawet jeśli agent potrafi złożyć komendę, może zostać zatrzymany przez politykę “approval/allowlist” (zależnie od konfiguracji). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
**Wniosek:** w produkcyjnych setupach `exec` często jest “supervised”: albo wymaga potwierdzeń, albo działa tylko na allowliście, albo jest wyłączony. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 5) `elevated` (uruchomienie na hoście) ma dodatkowe bramki
|
||||
|
||||
* `elevated` to alias zachowania “uruchom na gateway host z pełnymi uprawnieniami”, ale **działa sensownie głównie wtedy, gdy sesja jest sandboxowana** (w przeciwnym razie bywa no‑op). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* Jest to dodatkowo “gated” przez `tools.elevated` i ewentualne override per-agent – oba muszą pozwalać. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
**Wniosek:** jeśli liczysz na “wyjście z sandboxa” przez `elevated`, to musisz to mieć jawnie włączone; w wielu środowiskach będzie to celowo zablokowane. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 6) `exec` nie daje prawdziwego TTY bez `pty: true` (a i tak bywa ograniczone)
|
||||
|
||||
* Dokumentacja wskazuje: “Need a real TTY? Set `pty: true`.” [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* To rozwiązuje część problemów z programami interaktywnymi, ale w praktyce nadal możesz wpadać na ograniczenia sandboxa / braku urządzeń / braku UI. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
**Wniosek:** `exec` nie jest idealne do narzędzi wymagających pełnej interakcji terminalowej, jeśli środowisko nie jest do tego przygotowane. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 7) `exec` może być “ucinane” przez loop‑detection (gdy agent zapętla tool‑calls)
|
||||
|
||||
* OpenClaw ma mechanizm loop‑detection, który może ostrzegać/blokować powtarzalne wywołania narzędzi bez postępu (można włączyć i konfigurować progi). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
**Wniosek:** jeśli agent wpada w pętlę `exec → poll → exec → poll`, system może to wykryć i zablokować. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## 8) Kluczowe “praktyczne” ograniczenie: ryzyko injection i brak automatycznej sanityzacji
|
||||
|
||||
To nie jest pojedyncza flaga, tylko fakt wynikający z charakteru `exec`:
|
||||
|
||||
* `exec` uruchamia **shell commands**, więc jeśli sklejasz komendę z surowego inputu usera, otwierasz się na injection. Dokumentacja narzędzi podkreśla, że `exec` to narzędzie w grupie “runtime” i wymaga świadomej polityki bezpieczeństwa (deny/allowlist/approvals). [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
* W docs “Creating Skills” jest ostrzeżenie: jeśli skill używa “bash/exec”, trzeba uważać na **arbitrary command injection** z niezaufanego inputu. [\[deepwiki.com\]](https://deepwiki.com/openclaw/openclaw/6.4-skills-system)
|
||||
|
||||
**Wniosek:** najtwardszym ograniczeniem “w praktyce” jest to, że w dobrym projekcie `exec` **musi** być ograniczone allowlistą + kontrolą parametrów. [\[deepwiki.com\]](https://deepwiki.com/openclaw/openclaw/6.4-skills-system), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
# Rekomendacja (krótko, produkcyjnie)
|
||||
|
||||
Jeśli chcesz używać `exec` w skillach “na serio”, to zwykle wygląda to tak:
|
||||
|
||||
1. `tools.profile` + `tools.allow/deny` ogranicza dostęp do `exec` tylko tam, gdzie naprawdę trzeba. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
2. Skill ma **allowlistę komend** + walidację argumentów + ograniczenie ścieżek do run‑folderu. (To jest najlepsza praktyka wynikająca z ryzyk `exec` i ostrzeżeń dot. injection). [\[deepwiki.com\]](https://deepwiki.com/openclaw/openclaw/6.4-skills-system), [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
3. Długie komendy → `process` musi być dostępny, inaczej long‑running flow się posypie. [\[blog.laozhang.ai\]](https://blog.laozhang.ai/en/posts/openclaw-custom-model)
|
||||
|
||||
***
|
||||
|
||||
## Dopytam jedno (żeby odpowiedzieć “pod Twoją konfigurację”, nie ogólnie)
|
||||
|
||||
U Ciebie `exec` ma działać **w sandboxie** czy **na hoście**? (I czy włączone jest `process`?)
|
||||
Na tej podstawie mogę zaproponować konkretny, bezpieczny zestaw: policy + allowlista + wzorce komend pod Twój use‑case.
|
||||
Reference in New Issue
Block a user