diff --git a/.github/DISCUSSION_TEMPLATE/feature-request.yml b/.github/DISCUSSION_TEMPLATE/feature-request.yml new file mode 100644 index 00000000..76a5be9b --- /dev/null +++ b/.github/DISCUSSION_TEMPLATE/feature-request.yml @@ -0,0 +1,28 @@ +labels: [] +body: + - type: textarea + id: proposal + attributes: + label: Proposal + value: | + # Summary + + A brief explanation of the proposal. + + # Background and motivation + + Include the context that explains why this proposal matters. + What problem are you trying to solve? Who is affected? + + # Goals + + List the outcomes this proposal should achieve. + + - + + # Example + + If the proposal changes an API or workflow, include a small example. + Otherwise, omit this section. + validations: + required: true diff --git a/.github/ISSUE_TEMPLATE/01-bug-report.md b/.github/ISSUE_TEMPLATE/01-bug-report.md new file mode 100644 index 00000000..f76bdf77 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/01-bug-report.md @@ -0,0 +1,19 @@ +### Describe the bug + + + +### Expected behavior + + + +### Steps to reproduce + + + +1. +2. +3. + +### Environment + + diff --git a/.github/ISSUE_TEMPLATE/config.yml b/.github/ISSUE_TEMPLATE/config.yml new file mode 100644 index 00000000..ef11a3f5 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/config.yml @@ -0,0 +1,5 @@ +blank_issues_enabled: true +contact_links: + - name: Feature request or design discussion + url: https://github.com/cloudflare/computer/discussions/new?category=feature-request + about: Propose and discuss new features, improvements, and design changes. diff --git a/.github/pull_request_template.md b/.github/pull_request_template.md new file mode 100644 index 00000000..dfcd0f43 --- /dev/null +++ b/.github/pull_request_template.md @@ -0,0 +1,8 @@ +Thanks for your interest in Cloudflare Computer. + +This repository does not accept unsolicited pull requests. Please open one of the accepted contribution types instead: + +- Bug reports and fixes: https://github.com/cloudflare/computer/issues +- Feature requests and design proposals: https://github.com/cloudflare/computer/discussions + +Maintainers may close pull requests that do not come from an approved collaborator. If a maintainer asked you to open this pull request, they can add the `allow-pr` label and reopen it. diff --git a/.github/workflows/close-unrequested-prs.yml b/.github/workflows/close-unrequested-prs.yml new file mode 100644 index 00000000..9b73784d --- /dev/null +++ b/.github/workflows/close-unrequested-prs.yml @@ -0,0 +1,52 @@ +name: Close unrequested pull requests + +on: + pull_request_target: + types: [opened, reopened] + +permissions: + contents: read + issues: write + pull-requests: write + +jobs: + close: + runs-on: ubuntu-24.04 + steps: + - name: Close pull requests from unapproved contributors + uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0 + with: + script: | + const pullRequest = context.payload.pull_request; + const allowedAssociations = new Set(['OWNER', 'MEMBER', 'COLLABORATOR']); + const allowedBots = new Set(['dependabot[bot]', 'renovate[bot]']); + const allowedLabels = new Set(['allow-pr']); + + if (allowedAssociations.has(pullRequest.author_association)) { + return; + } + + if (allowedBots.has(pullRequest.user.login)) { + return; + } + + const labels = (pullRequest.labels || []).map((label) => label.name); + if (labels.some((label) => allowedLabels.has(label))) { + return; + } + + const { owner, repo } = context.repo; + const issue_number = pullRequest.number; + const body = [ + 'Thanks for your interest in Cloudflare Computer.', + '', + 'This repository does not accept unsolicited pull requests. Please use one of the accepted contribution paths instead:', + '', + '- Bug reports, regressions, and fix proposals: https://github.com/cloudflare/computer/issues/new/choose', + '- Feature requests, enhancements, and design proposals: https://github.com/cloudflare/computer/discussions', + '', + 'If a maintainer asked you to open this pull request, they can add the `allow-pr` label and reopen it.' + ].join('\n'); + + await github.rest.issues.createComment({ owner, repo, issue_number, body }); + await github.rest.pulls.update({ owner, repo, pull_number: issue_number, state: 'closed' }); diff --git a/AGENTS.md b/AGENTS.md index e8130118..28fa451a 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -4,7 +4,8 @@ - [`README.md`](README.md) — what this repo is and how the pieces fit together. -- [`CONTRIBUTING.md`](CONTRIBUTING.md) — setup, checks, commit and +- [`CONTRIBUTING.md`](CONTRIBUTING.md) — public contribution paths. +- [`COLLABORATORS.md`](COLLABORATORS.md) — setup, checks, commit and pull request conventions. The canonical source for the day-to-day workflow. - [`docs/README.md`](docs/README.md) — design specification. Forward- @@ -103,11 +104,11 @@ npm test --workspace @cloudflare/dofs -- src/foo.test.ts # one file ``` Full details, including typecheck and build commands, are in -[`CONTRIBUTING.md`](CONTRIBUTING.md). +[`COLLABORATORS.md`](COLLABORATORS.md). ## Commits and pull requests -Follow [`CONTRIBUTING.md`](CONTRIBUTING.md). The short version: +Follow [`COLLABORATORS.md`](COLLABORATORS.md). The short version: - One logical change per commit. - Imperative subject prefixed with the scope (`dofs:`, `rpc:`, `computer:`, diff --git a/COLLABORATORS.md b/COLLABORATORS.md new file mode 100644 index 00000000..cecdd658 --- /dev/null +++ b/COLLABORATORS.md @@ -0,0 +1,127 @@ +# Collaborator guide + +This document is for approved collaborators with pull request access. Public contribution paths are documented in [`CONTRIBUTING.md`](CONTRIBUTING.md). + +It covers the day-to-day mechanics: how to set up the repo, how to run checks, and how to shape commits and pull requests. + +## Setup + +Requirements: + +- Node 22 or newer. `packages/computerd` declares `"engines": { "node": ">=22" }`. +- npm. This repo uses npm workspaces, not pnpm or yarn. +- Linux with FUSE if you want to run `packages/computerd` end-to-end. The rest of the workspace builds and tests on macOS as well. +- Docker, optionally, for `examples/container`. + +Clone and install from the repo root: + +```bash +git clone https://github.com/cloudflare/computer.git +cd computer +npm install +``` + +`npm install` resolves all workspaces in one pass. Do not run `npm install` inside a single package. It creates a nested lockfile and confuses the workspace resolver. + +## Repository layout + +The repo is a small monorepo. Each package owns its own `README.md` with package-specific status and usage notes: + +- [`packages/dofs`](packages/dofs/) — Durable Object SQLite-backed virtual filesystem, sync protocol building blocks, and a `@platformatic/vfs` provider for Node. +- [`packages/rpc`](packages/rpc/) — capnweb-based wire types and server/client helpers shared between the Durable Object and `computerd`. +- [`packages/computerd`](packages/computerd/) — the `computerd` daemon: a FUSE mount plus HTTP/WebSocket RPC server that runs inside the sandbox container. +- [`packages/computer`](packages/computer/) — the top-level `@cloudflare/computer` package consumed by Durable Objects. +- [`packages/computer-computerd-linux-x64`](packages/computer-computerd-linux-x64/) — the prebuilt `computerd` binary for linux-x64, distributed for use in container images. + +[`docs/`](docs/) holds the design specification. It is forward-looking and has diverged from `main` in places. Treat it as intent, not as a description of the code today. + +## Code changes + +Touch the package that owns the behavior. Cross-package changes are fine, but group them into one logical change per commit. + +When you finish a task: + +- Update the affected package's `README.md` if its implementation status changes. +- Run the checks below. + +## Formatting and linting + +Biome handles both formatting and linting. From the repo root: + +```bash +npm run format # biome format --write . +npm run check # biome lint + formatter verification +``` + +`npm run format` is allowed to rewrite files. `npm run check` must exit zero before you push. If `check` complains, fix the underlying issue rather than silencing the rule. Disabled rules need a real justification. + +## Tests + +Run the package-level tests for whatever you touched. For the whole workspace: + +```bash +npm test +``` + +For a single package: + +```bash +npm test --workspace @cloudflare/dofs +``` + +For a single test file inside a package: + +```bash +npm test --workspace @cloudflare/dofs -- src/path/to/file.test.ts +``` + +`packages/computerd` includes FUSE-backed tests that only run on Linux. On other platforms they are skipped automatically. + +New behavior needs a test. Bug fixes need a reproduction test that failed before the fix. See [`.agents/skills/test-driven-development/SKILL.md`](.agents/skills/test-driven-development/SKILL.md) for the testing approach this repo follows. + +## Typecheck and build + +```bash +npm run typecheck # tsc --noEmit across workspaces +npm run build # library builds +npm run build:all # libraries, bundled binaries, docker images +``` + +`build:all` is the union of `build`, `build:bin`, and `build:docker`. Only run it if you need the binary or Docker artifacts. It is slow. + +## Commit messages + +Commit messages are read out of context, years later, by people with no memory of the change. Write them for that reader. + +The full guidance lives in [`.agents/skills/prose/SKILL.md`](.agents/skills/prose/SKILL.md). The short version: + +- **Subject line.** Imperative mood, 50 characters or fewer where possible, 72 hard maximum. No trailing period. Prefix with the package or scope: `dofs:`, `rpc:`, `computer:`, `computerd:`, `examples/think:`, `docs:`, `ci:`. Multiple scopes are joined with commas, as in `computerd, rpc: …`. +- **Blank line**, then a body wrapped at 72 characters. Explain what and why, not how. The diff already shows how. +- **One logical change per commit.** Do not bundle unrelated edits. +- **Self-contained.** No references to chat history, agent sessions, review threads, or sibling commit SHAs. A reader on `main` in five years should understand the commit from its message alone. +- **No marketing voice, no emojis, no headings or bulleted lists in the body.** Prose paragraphs. +- **American English** in prose. Code identifiers keep their original spelling. + +`git log` is the canonical style reference. Skim a page of it before your first commit. + +## Pull requests + +A pull request tells the story behind a set of commits. Full guidance lives in [`.agents/skills/pull-requests/SKILL.md`](.agents/skills/pull-requests/SKILL.md). The shape is: + +1. The problem the change is solving, with a link to the issue if one exists. +2. The solution and how it addresses the problem. +3. How a reviewer can verify it locally: a command, a snippet, or a description of the manual test. +4. The testing strategy: what is covered and what is not. +5. Documentation changes, if any. +6. Known follow-ups. + +Keep pull requests scoped to one logical change where you can. Do not include lists of changed files. The diff is right there. + +External pull requests are closed automatically unless they come from an owner, member, collaborator, Dependabot, Renovate, or carry the `allow-pr` label. Add `allow-pr` before reopening an external pull request that should go through review. + +## What not to commit + +- `node_modules/`, `dist/`, `artifacts/`. These are already ignored, but double-check `git status` before staging. +- `.env` and `.dev.vars`. Local secrets and per-developer settings stay on your machine. +- Editor or operating system scratch files. Add them to your global gitignore rather than to this repo's `.gitignore`. +- Generated `worker-configuration.d.ts` files, except for the copies checked in under `examples/`. diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 68636cf4..e7b50386 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -1,174 +1,35 @@ # Contributing -Thanks for working on the Cloudflare Computer prototype. This document -covers the day-to-day mechanics: how to set up the repo, how to run the -checks, and how to shape commits and pull requests. +Thanks for your interest in Cloudflare Computer. This repository accepts issues and discussions as the public contribution paths. It does not accept unsolicited pull requests. -Agents working in this repo should also read [`AGENTS.md`](AGENTS.md), -which points at the in-repo skills under [`.agents/skills/`](.agents/skills/). +## What to open -## Setup +Use one of these routes: -Requirements: +1. **Bug reports, regressions, and fix proposals** + - Open an issue: + - Include steps to reproduce, what you expected to happen, what happened instead, and any relevant package version, runtime, operating system, Worker, or Container setup. +2. **Feature requests, enhancements, and design proposals** + - Start a discussion: + - Describe the problem, the users affected, the outcome you want, and any API or workflow example that makes the proposal easier to evaluate. -- Node 22 or newer (`packages/computerd` declares `"engines": { "node": ">=22" }`). -- npm — this repo uses npm workspaces, not pnpm or yarn. -- Linux with FUSE if you want to run `packages/computerd` end-to-end. The - rest of the workspace builds and tests on macOS as well. -- Docker, optionally, for `examples/container`. - -Clone and install from the repo root: - -```bash -git clone https://github.com/cloudflare/computer.git -cd computer -npm install -``` - -`npm install` resolves all workspaces in one pass. Don't run `npm install` -inside a single package — it produces a nested lockfile and confuses -the workspace resolver. - -## Repository layout - -The repo is a small monorepo. Each package owns its own `README.md` -with package-specific status and usage notes: - -- [`packages/dofs`](packages/dofs/) — Durable Object SQLite-backed virtual - filesystem, sync protocol building blocks, and a `@platformatic/vfs` - provider for Node. -- [`packages/rpc`](packages/rpc/) — capnweb-based wire types and - server/client helpers shared between the Durable Object and `computerd`. -- [`packages/computerd`](packages/computerd/) — the `computerd` daemon: a FUSE mount plus - HTTP/WebSocket RPC server that runs inside the sandbox container. -- [`packages/computer`](packages/computer/) — the top-level - `@cloudflare/computer` package consumed by Durable Objects. -- [`packages/computer-computerd-linux-x64`](packages/computer-computerd-linux-x64/) — - the prebuilt `computerd` binary for linux-x64, distributed for use in - container images. - -[`docs/`](docs/) holds the design specification. It is forward-looking -and has diverged from `main` in places — treat it as intent, not as a -description of the code today. - -## Code changes - -Touch the package that owns the behavior. Cross-package changes are -fine, but group them into one logical change per commit. - -When you finish a task: - -- Update the affected package's `README.md` if its implementation - status changes. -- Run the checks below. - -## Formatting and linting - -Biome handles both formatting and linting. From the repo root: - -```bash -npm run format # biome format --write . -npm run check # biome lint + formatter verification -``` - -`npm run format` is allowed to rewrite files. `npm run check` must -exit zero before you push. If `check` complains, fix the underlying -issue rather than silencing the rule — disabled rules need a real -justification, not a shrug. - -## Tests - -Run the package-level tests for whatever you touched. For the whole -workspace: - -```bash -npm test -``` - -For a single package: - -```bash -npm test --workspace @cloudflare/dofs -``` - -For a single test file inside a package: - -```bash -npm test --workspace @cloudflare/dofs -- src/path/to/file.test.ts -``` - -`packages/computerd` includes FUSE-backed tests that only run on Linux. On -other platforms they're skipped automatically. - -New behavior needs a test. Bug fixes need a reproduction test that -failed before the fix. See [`.agents/skills/test-driven-development/SKILL.md`](.agents/skills/test-driven-development/SKILL.md) -for the testing approach this repo follows. - -## Typecheck and build - -```bash -npm run typecheck # tsc --noEmit across workspaces -npm run build # library builds -npm run build:all # libraries, bundled binaries, docker images -``` - -`build:all` is the union of `build`, `build:bin`, and `build:docker`. -Only run it if you actually need the binary or docker artifacts; it's -slow. - -## Commit messages - -Commit messages are read out of context, years later, by people with -no memory of the change. Write them for that reader. - -The full guidance lives in -[`.agents/skills/prose/SKILL.md`](.agents/skills/prose/SKILL.md). The -short version: +## Pull requests -- **Subject line.** Imperative mood, ≤ 50 characters where possible, - 72 hard maximum. No trailing period. Prefix with the package or - scope: `dofs:`, `rpc:`, `computer:`, `computerd:`, `examples/think:`, - `docs:`, `ci:`. Multiple scopes are joined with commas, as in - `computerd, rpc: …`. -- **Blank line**, then a body wrapped at 72 characters. Explain *what - and why*, not *how* — the diff already shows how. -- **One logical change per commit.** Don't bundle unrelated edits. -- **Self-contained.** No references to chat history, agent sessions, - review threads, or sibling commit SHAs. A reader on `main` in five - years should understand the commit from its message alone. -- **No marketing voice, no emojis, no headings or bulleted lists in - the body.** Prose paragraphs. -- **American English** in prose. Code identifiers keep their original - spelling. +Please do not open a pull request unless a maintainer has asked you to. Pull requests that do not come from an approved collaborator may be closed and redirected to an issue or discussion. -`git log` is the canonical style reference. Skim a page of it before -your first commit. +If you already have a patch, open an issue or discussion instead and include: -## Pull requests +- the problem the patch solves; +- the behavior change you propose; +- the tests or commands that prove the change works; +- any compatibility or migration concerns. -A pull request tells the story behind a set of commits. Full guidance -lives in [`.agents/skills/pull-requests/SKILL.md`](.agents/skills/pull-requests/SKILL.md); -the shape is: +Starting from the problem gives maintainers room to decide whether the change fits the project and how it should land. -1. The problem the change is solving, with a link to the issue if one - exists. -2. The solution and how it addresses the problem. -3. How a reviewer can verify it locally — a command, a snippet, or a - description of the manual test. -4. The testing strategy: what's covered, what isn't. -5. Documentation changes, if any. -6. Known follow-ups. +## Security reports -Keep pull requests scoped to one logical change where you can. Don't -include lists of changed files — the diff is right there. +Do not report security issues in public issues, discussions, or pull requests. Follow Cloudflare's vulnerability disclosure process instead: . -## What not to commit +## Collaborators -- `node_modules/`, `dist/`, `artifacts/`. These are already ignored, - but double-check `git status` before staging. -- `.env` and `.dev.vars`. Local secrets and per-developer settings - stay on your machine. -- Editor or OS scratch files. Add them to your global gitignore - rather than to this repo's `.gitignore`. -- Generated `worker-configuration.d.ts` files, except for the copies - checked in under `examples/`. +Approved collaborators should follow [`COLLABORATORS.md`](COLLABORATORS.md) for setup, checks, commit messages, and pull request conventions. diff --git a/README.md b/README.md index d34b0984..758062fc 100644 --- a/README.md +++ b/README.md @@ -42,9 +42,9 @@ If you want to build on Cloudflare Computer, install package's README — it has the installation steps, the entrypoint map, and worked examples of the `fs` and `runtime` surfaces. -To work on this repository itself, see -[`CONTRIBUTING.md`](CONTRIBUTING.md) for setup, build, and test -instructions. +To contribute feedback, see [`CONTRIBUTING.md`](CONTRIBUTING.md). +Approved collaborators should follow [`COLLABORATORS.md`](COLLABORATORS.md) +for setup, build, and test instructions. ## Examples @@ -113,8 +113,14 @@ to reproduce them. ## Contributing -See [`CONTRIBUTING.md`](CONTRIBUTING.md) for setup, formatting, -testing, commit message, and pull request conventions. +We accept bug reports, fix proposals, feature requests, and design +proposals through issues and discussions. We do not accept unsolicited +pull requests. See [`CONTRIBUTING.md`](CONTRIBUTING.md) for the public +contribution paths. + +Approved collaborators should follow +[`COLLABORATORS.md`](COLLABORATORS.md) for setup, formatting, testing, +commit message, and pull request conventions. If you're working in this repo as an agent, start with [`AGENTS.md`](AGENTS.md) and the skills under