[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"project-75002":3},{"id":4,"name":5,"fullName":6,"owner":7,"repo":5,"description":8,"homepage":9,"htmlUrl":10,"language":11,"languages":10,"totalLinesOfCode":10,"stars":12,"forks":13,"watchers":14,"openIssues":15,"contributorsCount":16,"subscribersCount":16,"size":16,"stars1d":15,"stars7d":17,"stars30d":18,"stars90d":16,"forks30d":16,"starsTrendScore":19,"compositeScore":20,"rankGlobal":10,"rankLanguage":10,"license":21,"archived":22,"fork":22,"defaultBranch":23,"hasWiki":22,"hasPages":22,"topics":24,"createdAt":10,"pushedAt":10,"updatedAt":25,"readmeContent":26,"aiSummary":27,"trendingCount":16,"starSnapshotCount":16,"syncStatus":28,"lastSyncTime":29,"discoverSource":30},75002,"lobster","openclaw\u002Flobster","openclaw","Lobster is a Openclaw-native workflow shell: a typed, local-first “macro engine” that turns skills\u002Ftools into composable pipelines and safe automations—and lets Openclaw call those workflows in one step.","https:\u002F\u002Fdocs.openclaw.ai\u002Ftools\u002Flobster",null,"TypeScript",1224,274,21,1,0,5,22,3,20.32,"MIT License",false,"main",[],"2026-06-12 02:03:31","# 🦞 Lobster\n\nAn OpenClaw-native workflow shell: typed (JSON-first) pipelines, jobs, and approval gates.\n\n\n## Example of Lobster at work\nOpenClaw (or any other AI agent) can use `lobster` as a workflow engine and avoid re-planning every step — saving tokens while improving determinism and resumability.\n\n### Watching a PR that hasn't had changes\n```\nnode bin\u002Flobster.js \"workflows.run --name github.pr.monitor --args-json '{\\\"repo\\\":\\\"openclaw\u002Fopenclaw\\\",\\\"pr\\\":1152}'\"\n[\n  {\n    \"kind\": \"github.pr.monitor\",\n    \"repo\": \"openclaw\u002Fopenclaw\",\n    \"prNumber\": 1152,\n    \"key\": \"github.pr:openclaw\u002Fopenclaw#1152\",\n    \"changed\": false,\n    \"summary\": {\n      \"changedFields\": [],\n      \"changes\": {}\n    },\n    \"prSnapshot\": {\n      \"author\": {\n        \"id\": \"MDQ6VXNlcjE0MzY4NTM=\",\n        \"is_bot\": false,\n        \"login\": \"vignesh07\",\n        \"name\": \"Vignesh\"\n      },\n      \"baseRefName\": \"main\",\n      \"headRefName\": \"feat\u002Flobster-plugin\",\n      \"isDraft\": false,\n      \"mergeable\": \"MERGEABLE\",\n      \"number\": 1152,\n      \"reviewDecision\": \"\",\n      \"state\": \"OPEN\",\n      \"title\": \"feat: Add optional lobster plugin tool (typed workflows, approvals\u002Fresume)\",\n      \"updatedAt\": \"2026-01-18T20:16:56Z\",\n      \"url\": \"https:\u002F\u002Fgithub.com\u002Fopenclaw\u002Fopenclaw\u002Fpull\u002F1152\"\n    }\n  }\n]\n```\n### And a PR that has a state change (in this case an approved PR)\n\n```\n node bin\u002Flobster.js \"workflows.run --name github.pr.monitor --args-json '{\\\"repo\\\":\\\"openclaw\u002Fopenclaw\\\",\\\"pr\\\":1200}'\"\n[\n  {\n    \"kind\": \"github.pr.monitor\",\n    \"repo\": \"openclaw\u002Fopenclaw\",\n    \"prNumber\": 1200,\n    \"key\": \"github.pr:openclaw\u002Fopenclaw#1200\",\n    \"changed\": true,\n    \"summary\": {\n      \"changedFields\": [\n        \"number\",\n        \"title\",\n        \"url\",\n        \"state\",\n        \"isDraft\",\n        \"mergeable\",\n        \"reviewDecision\",\n        \"updatedAt\",\n        \"baseRefName\",\n        \"headRefName\"\n      ],\n      \"changes\": {\n        \"number\": {\n          \"from\": null,\n          \"to\": 1200\n        },\n        \"title\": {\n          \"from\": null,\n          \"to\": \"feat(tui): add syntax highlighting for code blocks\"\n        },\n        \"url\": {\n          \"from\": null,\n          \"to\": \"https:\u002F\u002Fgithub.com\u002Fopenclaw\u002Fopenclaw\u002Fpull\u002F1200\"\n        },\n        \"state\": {\n          \"from\": null,\n          \"to\": \"MERGED\"\n        },\n        \"isDraft\": {\n          \"from\": null,\n          \"to\": false\n        },\n        \"mergeable\": {\n          \"from\": null,\n          \"to\": \"UNKNOWN\"\n        },\n        \"reviewDecision\": {\n          \"from\": null,\n          \"to\": \"\"\n        },\n        \"updatedAt\": {\n          \"from\": null,\n          \"to\": \"2026-01-19T05:06:09Z\"\n        },\n        \"baseRefName\": {\n          \"from\": null,\n          \"to\": \"main\"\n        },\n        \"headRefName\": {\n          \"from\": null,\n          \"to\": \"feat\u002Ftui-syntax-highlighting\"\n        }\n      }\n    },\n    \"prSnapshot\": {\n      \"author\": {\n        \"id\": \"MDQ6VXNlcjE0MzY4NTM=\",\n        \"is_bot\": false,\n        \"login\": \"vignesh07\",\n        \"name\": \"Vignesh\"\n      },\n      \"baseRefName\": \"main\",\n      \"headRefName\": \"feat\u002Ftui-syntax-highlighting\",\n      \"isDraft\": false,\n      \"mergeable\": \"UNKNOWN\",\n      \"number\": 1200,\n      \"reviewDecision\": \"\",\n      \"state\": \"MERGED\",\n      \"title\": \"feat(tui): add syntax highlighting for code blocks\",\n      \"updatedAt\": \"2026-01-19T05:06:09Z\",\n      \"url\": \"https:\u002F\u002Fgithub.com\u002Fopenclaw\u002Fopenclaw\u002Fpull\u002F1200\"\n    }\n  }\n]\n```\n\n## Goals\n\n\n- Typed pipelines (objects\u002Farrays), not text pipes.\n- Local-first execution.\n- No new auth surface: Lobster must not own OAuth\u002Ftokens.\n- Composable macros that OpenClaw (or any agent) can invoke in one step to save tokens.\n\n## Quick start\n\nFrom this folder:\n\n- `pnpm install`\n- `pnpm test`\n- `pnpm lint`\n- `node .\u002Fbin\u002Flobster.js --help`\n- `node .\u002Fbin\u002Flobster.js doctor`\n- `node .\u002Fbin\u002Flobster.js \"exec --json --shell 'echo [1,2,3]' | where '0>=0' | json\"`\n\n### Notes\n\n- `pnpm test` runs `tsc` and then executes tests against `dist\u002F`.\n- `bin\u002Flobster.js` prefers the compiled entrypoint in `dist\u002F` when present.\n## Commands\n\n- `exec`: run OS commands\n- `exec --stdin raw|json|jsonl`: feed pipeline input into subprocess stdin\n- `where`, `pick`, `head`: data shaping\n- `json`, `table`: renderers\n- `approve`: approval gate (TTY prompt or `--emit` for OpenClaw integration)\n\n## Next steps\n\n- OpenClaw integration: ship as an optional OpenClaw plugin tool.\n\n## Workflow files\n\nLobster workflow files are meant to read like small scripts:\n\n- `run:` or `command:` for deterministic shell\u002FCLI steps\n- `pipeline:` for native Lobster stages like `llm.invoke`\n- `approval:` for hard workflow gates between steps\n- `stdin: $step.stdout` or `stdin: $step.json` to pass data forward\n\n```\nlobster run path\u002Fto\u002Fworkflow.lobster\nlobster run --file path\u002Fto\u002Fworkflow.lobster --args-json '{\"tag\":\"family\"}'\n```\n\nExample file:\n\n```yaml\nname: jacket-advice\nargs:\n  location:\n    default: Phoenix\nsteps:\n  - id: fetch\n    run: weather --json ${location}\n\n  - id: confirm\n    approval: Want jacket advice from the LLM?\n    stdin: $fetch.json\n\n  - id: advice\n    pipeline: >\n      llm.invoke --prompt \"Given this weather data, should I wear a jacket?\n      Be concise and return JSON.\"\n    stdin: $fetch.json\n    when: $confirm.approved\n```\n\nNotes:\n\n- `run:` and `command:` are equivalent; `run:` is the preferred spelling for new files.\n- `pipeline:` shares the same args\u002Fenv\u002Fresults model as shell steps, so later steps can still reference `$step.stdout` or `$step.json`.\n- If you need a human checkpoint before an LLM call, use a dedicated `approval:` step in the workflow file rather than `approve` inside the nested pipeline.\n- `cwd`, `env`, `stdin`, `when`, and `condition` work for both shell and pipeline steps.\n- Use `retry`, `timeout_ms`, and `on_error` per step to control transient-failure behavior and recovery.\n- Approval steps can optionally enforce identity constraints:\n  - `approval.required_approver` (or `requiredApprover`) requires an exact approver id.\n  - `approval.require_different_approver` (or `requireDifferentApprover`) requires approver id to differ from initiator.\n  - `approval.initiated_by` (or `initiatedBy`) sets the initiator id for comparison.\n  - `LOBSTER_APPROVAL_INITIATED_BY` can provide a default initiator id at run time.\n  - `LOBSTER_APPROVAL_APPROVED_BY` is used at resume\u002Fapproval time for identity checks.\n\n## Visualizing workflows\n\nUse `lobster graph` to inspect workflow structure before execution.\n\n```bash\nlobster graph --file path\u002Fto\u002Fworkflow.lobster\nlobster graph --file path\u002Fto\u002Fworkflow.lobster --format mermaid\nlobster graph --file path\u002Fto\u002Fworkflow.lobster --format dot\nlobster graph --file path\u002Fto\u002Fworkflow.lobster --format ascii\nlobster graph --file path\u002Fto\u002Fworkflow.lobster --args-json '{\"location\":\"Seattle\"}'\n```\n\nWhat gets visualized:\n\n- each workflow step as a node (`run`, `pipeline`, `approval`, etc.)\n- data-flow edges from `stdin: $step.stdout` \u002F `$step.json` references\n- conditional dependencies from `when:` \u002F `condition:` expressions\n- approval gates as diamond-shaped nodes in `mermaid` and `dot` output\n\nFormat notes:\n\n- `mermaid` (default): emits `flowchart TD` text for GitHub\u002FMarkdown rendering\n- `dot`: emits Graphviz DOT syntax\n- `ascii`: emits a terminal-friendly node\u002Fedge list\n\n## Calling LLMs from workflows\n\nUse `llm.invoke` from a native `pipeline:` step for model-backed work:\n\n```bash\nllm.invoke --prompt 'Summarize this diff'\nllm.invoke --provider openclaw --prompt 'Summarize this diff'\nllm.invoke --provider pi --prompt 'Summarize this diff'\n```\n\nProvider resolution order:\n\n- `--provider`\n- `LOBSTER_LLM_PROVIDER`\n- auto-detect from environment\n\nBuilt-in providers today:\n\n- `openclaw` via `OPENCLAW_URL` \u002F `OPENCLAW_TOKEN`\n- `pi` via `LOBSTER_PI_LLM_ADAPTER_URL` (typically supplied by the Pi extension)\n- `http` via `LOBSTER_LLM_ADAPTER_URL`\n\n`llm_task.invoke` remains available as a backward-compatible alias for the OpenClaw provider.\n\n### `pipeline:` vs `run:` for LLM calls\n\n- Use `pipeline:` for `llm.invoke` and `llm_task.invoke` (they are Lobster pipeline stages, not shell executables).\n- Use `run:` only for real binaries in your shell (for example `openclaw.invoke`).\n\nExample (`stdin` from a prior step is passed to the LLM as artifacts):\n\n```yaml\nsteps:\n  - id: make_words\n    run: echo \"One two three four five six\"\n\n  - id: count_words\n    pipeline: llm_task.invoke --prompt \"How many words have been pasted below?\"\n    stdin: $make_words.stdout\n```\n\n## Calling OpenClaw tools from workflows\n\nShell `run:` steps execute in your system shell, so OpenClaw tool calls there must be real executables.\n\nIf you install Lobster via npm\u002Fpnpm, it installs a small shim executable named:\n\n- `openclaw.invoke` (preferred)\n- `clawd.invoke` (alias)\n\nThese shims forward to the Lobster pipeline command of the same name.\n\n### Example: invoke llm-task\n\nPrereqs:\n\n- `OPENCLAW_URL` points at a running OpenClaw gateway\n- optionally `OPENCLAW_TOKEN` if auth is enabled\n\n```bash\nexport OPENCLAW_URL=http:\u002F\u002F127.0.0.1:18789\n# export OPENCLAW_TOKEN=...\n```\n\nIn a workflow:\n\n```yaml\nname: hello-world\nsteps:\n  - id: greeting\n    run: >\n      openclaw.invoke --tool llm-task --action json --args-json '{\"prompt\":\"Hello\"}'\n```\n\n### Passing data between steps (no temp files)\n\nUse `stdin: $stepId.stdout` to pipe output from one step into the next.\n\n## Args and shell-safety\n\n`${arg}` substitution is a raw string replace into the shell command text.\n\nFor anything that may contain quotes, `$`, backticks, or newlines, prefer env vars:\n\n- every resolved workflow arg is exposed as `LOBSTER_ARG_\u003CNAME>` (uppercased, non-alnum → `_`)\n- the full args object is also available as `LOBSTER_ARGS_JSON`\n\nExample:\n\n```yaml\nargs:\n  text:\n    default: \"\"\nsteps:\n  - id: safe\n    env:\n      TEXT: \"$LOBSTER_ARG_TEXT\"\n    command: |\n      jq -n --arg text \"$TEXT\" '{\"result\": $text}'\n```\n","Lobster 是一个Openclaw原生的工作流壳，它将技能和工具转换为可组合的管道和安全自动化，并允许Openclaw在一个步骤中调用这些工作流。其核心功能包括类型化的（JSON优先）管道、任务和审批门控机制，使得AI代理如OpenClaw可以使用Llobster作为工作流引擎来避免每一步骤的重新规划，从而节省资源并提高确定性和可恢复性。特别适合需要高效管理和自动化GitHub Pull Requests监控等场景的应用，比如开发团队希望自动化处理代码审查流程时。",2,"2026-06-11 03:51:54","high_star"]