I gave my open-source project an AI crew that cannot touch GitHub Jahaan Suthar, a computer science student in Chennai, built Steward Crew, an open-source hackathon project on Switch that runs three AI agents across Discord and Slack alongside a non-AI "Ledger" component holding the only GitHub token. The agents can only file proposals as numbered cards, which act on GitHub solely when a maintainer types an approval command such as `approve 7`. In a test run with simulated contributors, the system filed ten cards in under two minutes, assigning three claims, releasing two stale claims, and routing two suspicious pull requests to a reviewer agent. How I built Steward Crew on Switch: three AI agents in Discord and Slack, one plain-Python Ledger, and a maintainer who types approve 7 . Hi, I'm Jahaan Suthar, a computer science student from Chennai. Every time I open an open-source project, I see maintainers buried in comments and claims instead of writing code. So for the Flip the Switch hackathon, I built them a crew. It is Monday morning on a small open-source project. Overnight, fourteen people commented "can I work on this?". Three of them want the same issue. One account, two days old, claimed four issues and opened a 600-line pull request that rewrites the README with rocket emoji. Someone who claimed the Windows docs last week has gone quiet. None of this is code. All of it lands on the maintainer before they can write any. I wanted an AI crew to take that work off them, without ever letting an AI do something on GitHub that a person did not approve. The rule I built everything around fits on one line: AI proposes, the Ledger acts, a maintainer decides. Here it is working, in under three minutes: Steward Crew is three AI agents and one program that is not AI, working across Discord and Slack through Switch. | Who | Where | What it does | |---|---|---| | Stu AI | Discord help , public | Answers newcomers from the real code, finds them a free issue, and files the request to assign it. Says it is an AI. | | Steward AI | Slack maintainers , private | Every morning: who claimed what, which claims went quiet, which issues are contested, which pull requests look off. One proposal per decision. | | Reviewer AI | Slack maintainers | Reads a flagged pull request against its issue and the code, and drafts a review or a polite close. | | Ledger not AI | Slack maintainers | The only part with a GitHub token. Posts each proposal as a numbered card and acts only when a maintainer types approve 7 . | The AI agents can only file proposals. The Ledger turns each one into a card, and only a maintainer's approve makes it act on GitHub. On a test run with a busy week of made-up contributors, Steward's morning summary filed ten cards in under two minutes. It assigned three new claims and gave a contested issue to the person who asked first, with a kind note to the other pointing at free issues. It released two claims that had been quiet for 70 and 96 hours, and drafted a one-claim-rule note for an account holding four. It handed the two suspicious pull requests to the Reviewer. I approved four cards with one line: approve 1 4 5 7 . This is the part I wish I had read on day one. Everything below ran on a MacBook Air with Switch Console's local server v0.40.1 . help . Switch turns a channel into a room the first time someone talks in it. Two errors I hit: Unknown Guild 10004 means the Guild ID is wrong, and LoginFailure means the token is. To change the token, use Disconnect app and connect again. Install the Switch Slack app, then in your private maintainers channel type /invite @Agent Switch . That channel is now a room. Do it in the channel you mean: my first room was all-steward-maintainers by accident. A Switch template is one YAML file: the rooms it needs as parameters, and the agents with their instructions, tools and rooms. Mine, trimmed: version: 1 params: help room: type: room label: "Community room Discord help " default: help, " help" maintainers room: type: room label: "Maintainers room Slack maintainers " agents: - name: stu display name: Stu AI directory: "{$agents dir}/{agent}" join: "{help room}" advanced config: tools: Read, Grep, Glob, Bash disallowedTools: "Write", "Edit", "NotebookEdit", "WebFetch", "WebSearch" maxTurns: 25 instructions: | You are Stu, the AI helper for an open-source project... In Switch Console: Templates , Import template , choose the file, then Use template and Create agents . Switch creates the agents, gives each its own folder, and puts them in the rooms. Quote any label that contains . In YAML an unquoted starts a comment, and my labels came out cut off. Switch agents do not have to be AI. The Ledger is a small Python program that registers with the local Switch server as an always-on agent and opens a WebSocket to its rooms. It reads every message in maintainers , not only the ones that name it. In Slack, invite-agent @ledger puts it in the room. | Command | What it does | |---|---| | invite-agent @ledger | Adds an agent to the room | | reset @stu | Starts the agent's session fresh, after you change its settings | | follow-ups off | Agents answer only when someone @-mentions them | I needed follow-ups off in the maintainers room. By default, Switch sends your next message without an @ to the agent you just talked to. So my approve 11 12 reached the Reviewer, which tried to be helpful about it. A prompt that says "never post on GitHub" is a wish, not a guarantee. Every rule here is enforced by code, by Claude Code, or by Switch itself. Only the Ledger holds a GitHub token. It is a fine-grained token for one repository, kept in the macOS Keychain. The agents never see it. The Ledger also keeps a copy of the code fresh for the agents to read, passing the token to git one command at a time, so there is nothing in .git/config to borrow. The agents' tools are locked down. In the template they get Read, Grep, Glob and Bash, and no editing or web tools. steward-ledger crew then writes Claude Code permission rules into each agent's folder: the steward command is allowed, and gh , git push , curl , the Keychain and the Ledger's files are denied. Rules are code, not prompts. "One open claim per newcomer" and "a claim is quiet after 48 hours" live in policy.yaml and are computed in plain Python. The spam checks on a pull request no linked issue, no tests, boilerplate phrases are too. The AI explains and drafts. It does not decide what the rules are. Every action is a numbered card. The card says what will happen, why, and the exact text that will be posted. Maintainers answer with approve 7 , decline 7