{"id":50988305,"url":"https://github.com/hellodword/webvibe","last_synced_at":"2026-06-19T22:31:35.688Z","repository":{"id":363150783,"uuid":"1257345400","full_name":"hellodword/webvibe","owner":"hellodword","description":null,"archived":false,"fork":false,"pushed_at":"2026-06-07T17:45:55.000Z","size":219,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"master","last_synced_at":"2026-06-07T18:15:27.729Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/hellodword.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":"docs/security.md","support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-06-02T15:36:26.000Z","updated_at":"2026-06-07T17:45:59.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/hellodword/webvibe","commit_stats":null,"previous_names":["hellodword/webvibe"],"tags_count":null,"template":false,"template_full_name":null,"purl":"pkg:github/hellodword/webvibe","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hellodword%2Fwebvibe","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hellodword%2Fwebvibe/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hellodword%2Fwebvibe/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hellodword%2Fwebvibe/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/hellodword","download_url":"https://codeload.github.com/hellodword/webvibe/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/hellodword%2Fwebvibe/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34550858,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-19T02:00:06.005Z","response_time":61,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2026-06-19T22:31:35.459Z","updated_at":"2026-06-19T22:31:35.679Z","avatar_url":"https://github.com/hellodword.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# webvibe\n\n`webvibe` is a local, policy-driven MCP relay for ChatGPT Web coding sessions. It exposes a stable OAuth/MCP endpoint, loads a policy, and publishes only the tools that policy allows. The relay is not an agent runtime and does not expose a general shell by default.\n\nThe default surface is shaped around ChatGPT Web host constraints: tool descriptors can be stale, high-risk calls can be blocked before they reach the relay, outputs can be truncated by the host, and the UI may ask for confirmation. `webvibe` therefore favors sanitized preflight, read-first inspection, fixed task IDs, preview-then-apply file changes, and visible manual completion with `/resume`.\n\n## Quick start\n\nRequirements: Node.js 20 or newer, plus a workspace you are willing to expose through the configured policy.\n\n```bash\nnpm install\nnpm run build\nnpm test\n\ncp config.example.yaml config.yaml\nexport WEBVIBE_PAIRING_CODE=\"$(openssl rand -base64 24)\"\n\nnpm run dev -- --config config.yaml\n```\n\n`server.publicBaseUrl` must be reachable by ChatGPT Web. For local development this is normally a tunnel URL that forwards to `server.listen`.\n\nAfter the server starts, connect ChatGPT Web to the configured `publicBaseUrl`. The OAuth authorization page asks for the pairing code from `WEBVIBE_PAIRING_CODE` or from the configured pairing-code source.\n\nFor a built run:\n\n```bash\nnpm run build\nnpm run start -- --config config.yaml\n```\n\n## Configuration\n\nThe example config is intentionally small:\n\n```yaml\nversion: 1\nserver:\n  listen: \"127.0.0.1:3000\"\n  publicBaseUrl: \"https://example.ngrok.app\"\n  stateDir: \"~/.webvibe\"\n  mode: \"dev\"\nworkspace:\n  root: \".\"\nauth:\n  pairingCodeEnv: \"WEBVIBE_PAIRING_CODE\"\n  pairingFailures:\n    maxAttempts: 5\n    windowSeconds: 600\n  accessTokenTtlDays: 30\n```\n\nImportant rules:\n\n- `--config \u003cpath\u003e` is required.\n- `server.mode` and `server.policy` are mutually exclusive.\n- If neither is set, the server uses the built-in `read-only` policy.\n- Exactly one pairing-code source must be configured: `auth.pairingCode`, `auth.pairingCodeEnv`, or `auth.pairingCodeFile`.\n- The pairing code `123456` is rejected at startup.\n- Runtime state goes under `server.stateDir`; workspace task logs go under `.webvibe/task-logs/`.\n\n## Built-in modes\n\n| Mode        | Default surface                                                                                                                    |\n| ----------- | ---------------------------------------------------------------------------------------------------------------------------------- |\n| `read-only` | `workspace.context`, `workspace.scan`, `workspace.symbols`, `fs.*`, Git inspection and `git.commit_preview`, `diagnostics.health`. |\n| `dev`       | Everything in `read-only`, plus `file.change_preview`, `file.change_apply`, `manual.*`, `task.*`, and `git.commit`.                |\n\nDefault `dev` mode uses one logical file change per preview/apply call. Batch change tools exist in the contract registry for custom policies, but the built-in `dev` policy does not expose them.\n\n## Default coding flow\n\nA normal ChatGPT Web session should:\n\n1. Call `workspace.context`.\n2. Inspect with `workspace.scan`, `fs.tree`, `fs.search`, `fs.read`, `fs.read_many`, and `fs.stat`.\n3. Call `task.list` before `task.run`; use `task.explain` when routing is unclear.\n4. Preview workspace writes with `file.change_preview`.\n5. Apply only with the matching `file.change_apply` `previewHash`.\n6. Use `git.commit_preview` before `git.commit`.\n7. Use `manual.prepare`, visible user instructions, `manual.gate`, and `/resume` when the host blocks a required action or no fixed tool/task can perform it.\n\n## Development commands\n\n```bash\nnpm run build\nnpm test\nnpm run lint\nnpm run audit\nnpm run policy:schema\nnpm run generate:tools\n```\n\n`npm run generate:tools` produces exact tool contract reference files from `src/tools/contracts`. Those generated files are reference artifacts, not hand-authored narrative documentation.\n\n## Documents\n\n- [Architecture](docs/architecture.md)\n- [Workflows](docs/workflows.md)\n- [ChatGPT Web Host Limits](docs/chatgpt-web-known-limits.md)\n- [Policy and Security](docs/policy-security.md)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fhellodword%2Fwebvibe","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fhellodword%2Fwebvibe","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fhellodword%2Fwebvibe/lists"}