/SKILL.md
Runtime framework for launching interactive browser-based webview UIs that communicate bidirectionally with the CLI agent via structured JSON data contracts. Use when: (1) The agent needs human-in-the-loop approval or review of proposed changes, (2) Displaying rich interactive dashboards, visualizations, or architecture diagrams, (3) Collecting structured user input via forms, wizards, or configuration panels, (4) Any task requiring a browser-based UI that exchanges data with the CLI agent. Provides a local HTTP+WebSocket server, file-based JSON data contract in the CWD, a client-side SDK, and bash helper scripts for agent integration.
npx skillsauth add techtoboggan/openwebgoggles openwebgogglesInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Launch browser-based interactive UIs from OpenCode skills with bidirectional agent communication.
bash scripts/start_webview.sh --app approval-review
This creates .openwebgoggles/ in the CWD, starts the server, and opens the browser.
bash scripts/write_state.sh '{"version":1,"status":"pending_review","updated_at":"2026-02-19T10:00:00Z","title":"Review Changes","data":{"files":[{"path":"src/main.py","summary":"Added error handling"}]},"actions_requested":[{"id":"approve","type":"approve","label":"Approve"},{"id":"reject","type":"reject","label":"Reject"}]}'
ACTIONS=$(bash scripts/wait_for_action.sh --timeout 300)
echo "$ACTIONS" # JSON with user's approve/reject/input responses
bash scripts/stop_webview.sh
Agent (bash) ←→ .openwebgoggles/*.json ←→ Server (Python) ←→ Browser (SDK + App)
state.json (agent→webview), actions.json (webview→agent), manifest.json (session metadata)All files live in .openwebgoggles/ within the current working directory.
| File | Direction | Purpose |
|------|-----------|---------|
| manifest.json | Bidirectional | Session config: which app, ports, session token |
| state.json | Agent → Webview | Current state, data payload, requested actions |
| actions.json | Webview → Agent | User decisions and input responses |
initializing — Server starting upready — Webview loaded, waiting for agent to send datapending_review — Agent has data for user to reviewwaiting_input — Agent needs user input to continueprocessing — Agent is working on user's responsecompleted — Workflow finishederror — Something went wrong| Script | Usage |
|--------|-------|
| start_webview.sh --app <name> [--port <N>] [--no-browser] | Start server and open browser |
| stop_webview.sh | Graceful shutdown via PID file |
| write_state.sh '<json>' or write_state.sh --file <path> | Atomic write to state.json |
| read_actions.sh [--clear] | Read actions.json, optionally clear after reading |
| wait_for_action.sh [--timeout <secs>] [--action-type <type>] | Block until user acts |
| init_webview_app.sh <name> [--dest <dir>] | Scaffold a new webview app from template |
dynamic App — No Custom Code NeededUse --app dynamic for any HITL UI. Write a UI schema into state.json and the dynamic renderer builds the interface automatically. No HTML/JS required.
bash scripts/start_webview.sh --app dynamic
bash scripts/write_state.sh "$(cat <<'EOF'
{
"version": 1,
"status": "waiting_input",
"title": "Deploy Configuration",
"message": "Review and confirm the deployment settings.",
"data": {
"ui": {
"sections": [
{
"type": "form",
"title": "Settings",
"columns": 2,
"fields": [
{ "key": "environment", "label": "Environment", "type": "select",
"options": ["staging", "production"], "value": "staging" },
{ "key": "replicas", "label": "Replicas", "type": "number",
"value": 2, "min": 1, "max": 10 },
{ "key": "tag", "label": "Docker Tag", "type": "text",
"value": "v1.4.2", "placeholder": "e.g. v1.2.3" },
{ "key": "notes", "label": "Release Notes", "type": "textarea",
"placeholder": "Optional notes..." }
],
"actions": [
{ "id": "deploy", "type": "submit", "label": "Deploy", "style": "success" },
{ "id": "cancel", "type": "reject", "label": "Cancel" }
]
}
]
}
},
"actions_requested": []
}
EOF
)"
RESULT=$(bash scripts/wait_for_action.sh --timeout 120)
# $RESULT contains { action_id, type, value: { environment, replicas, tag, notes } }
Section types:
| type | Purpose |
|------|---------|
| form | Input fields with submit actions. Collected values sent as action value. |
| items | List of items, each with per-item action buttons (e.g. approve/reject each). |
| text | Static message/info block. |
| actions | Standalone action buttons only. |
Field types: text, textarea, number, select, checkbox, email, url, static
Field properties:
key — identifier returned in action valuelabel — display labeltype — input typevalue / default — initial valueplaceholder — hint textoptions — for select: array of strings or [{value, label}] objectsdescription — helper text shown below fieldrows — for textarea heightmono — for static fields: monospace fontAction button styles: primary, success, danger, warning, ghost
(also accepts semantic types: approve, reject, confirm, submit, delete)
Items section example:
{
"type": "items",
"title": "Pending PRs",
"items": [
{ "id": "pr-42", "title": "Fix auth bug", "subtitle": "#42 · main ← feat/auth",
"actions": [
{ "id": "merge", "type": "approve", "label": "Merge", "style": "success" },
{ "id": "close", "type": "reject", "label": "Close", "style": "danger" }
]
}
]
}
bash scripts/init_webview_app.sh my-dashboardindex.html, app.js, style.css in the generated directory<script src="/sdk/openwebgoggles-sdk.js"></script>
<script>
const wv = new OpenWebGoggles();
wv.connect().then(() => {
wv.onStateUpdate((state) => {
// Render your UI based on state.data
// Show actions from state.actions_requested
});
});
function handleApprove() {
wv.approve('approve-all', { comment: 'Looks good' });
}
</script>
bash scripts/start_webview.sh --app my-dashboardSee references/integration-guide.md for detailed patterns. The basic flow:
See references/sdk-api.md for the full client SDK API.
tools
Use when work should span one or more detached tasks but still behave like one job with a single owner context. TaskFlow is the durable flow substrate under authoring layers like Lobster, ACPX, plugins, or plain code. Keep conditional logic in the caller; use TaskFlow for flow identity, child-task linkage, waiting state, revision-checked mutations, and user-facing emergence.
tools
# Lobster Lobster executes multi-step workflows with approval checkpoints. Use it when: - User wants a repeatable automation (triage, monitor, sync) - Actions need human approval before executing (send, post, delete) - Multiple tool calls should run as one deterministic operation ## When to use Lobster | User intent | Use Lobster? | | ------------------------------------------------------ | --------------------------
tools
# Lobster Lobster executes multi-step workflows with approval checkpoints. Use it when: - User wants a repeatable automation (triage, monitor, sync) - Actions need human approval before executing (send, post, delete) - Multiple tool calls should run as one deterministic operation ## When to use Lobster | User intent | Use Lobster? | | ------------------------------------------------------ | --------------------------
tools
A CLI tool for making authenticated requests to the X (Twitter) API. Use this skill when you need to post tweets, reply, quote, search, read posts, manage followers, send DMs, upload media, or interact with any X API v2 endpoint.