Backend that provisions per-user OpenCode + Gitea Docker pair via
dockerode and exposes the Grow Agent / sub-agent Rivet Kit actors
described in the PRD. Sub-agent workflows route through the parent
Grow Agent's OpenCode Docker.
- src/docker/manager.ts spawns growqr-gitea-<userId> and growqr-opencode-<userId>
- src/actors/{grow-agent,sub-agent,registry}.ts: Rivet Kit actors
- src/routes/{actors,opencode,git}.ts: PRD section 5.2-5.4 HTTP API
- docker-compose.yml runs rivet-engine + backend (mounts host Docker socket)
- PRD updated to lock in per-user OpenCode/Gitea Docker topology
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
15 KiB
Grow Agent Platform PRD
1. Overview
GrowQR is a multi-agent development and personal growth platform where every user gets a dedicated master agent called a Grow Agent. The Grow Agent owns the user's long-running context, memory, workflows, files, repositories, execution state, and progress.
The platform combines:
- A Slack-like frontend for chat, progress, and sub-agent channels.
- A dedicated Grow Agent per user, implemented as a Rivet Kit actor.
- Multiple specialized sub-agents per Grow Agent, also implemented as Rivet Kit actors.
- Git-backed memory and state using per-user repositories.
- A per-user OpenCode Docker container for coding and workflow execution.
- A per-user Gitea Docker container for internal Git hosting.
- Rivet Kit actors for durable state, orchestration, and actions.
- A frontend that pulls the Rivet Kit React/JS SDK to talk to actors directly.
- Backend APIs for auth, actor registry, Docker (OpenCode + Gitea) lifecycle management, payments, and product flows.
2. Product Goals
- Give every user a persistent AI workspace that can remember, plan, execute, and evolve over time.
- Store all user agent state in Git so memory, files, decisions, and workflow history are inspectable and versioned.
- Let a master Grow Agent orchestrate specialized sub-agents.
- Give each sub-agent isolated execution scope, logs, state, and optionally a Slack-style channel.
- Provide a frontend where users can talk to the Grow Agent, watch sub-agent progress, and trigger structured quests or pathways.
- Support paid access where payment provisions and starts the user's Grow Agent environment.
3. Core Concepts
3.1 User
A user is the primary account holder. Each user has:
- One active Grow Agent.
- One or more Git repositories for agent memory and workspace files.
- Access to a dedicated OpenCode execution environment.
- Access to a Slack-like UI with channels for master and sub-agent activity.
3.2 Grow Agent
The Grow Agent is the user's master agent and orchestration layer.
Responsibilities:
- Maintain user-level memory and context.
- Decide which sub-agent should handle a task.
- Trigger sub-agent workflows, routing every executable workflow through the user's OpenCode Docker.
- Track progress and state transitions.
- Commit important state changes to the user's Gitea Docker repo.
- Coordinate OpenCode sessions for code execution against its dedicated OpenCode Docker.
- Expose status to the frontend via the Rivet Kit React SDK.
The Grow Agent is implemented as a durable Rivet Kit actor. Each Grow Agent owns:
- Its own OpenCode Docker container (workflows + code execution).
- Its own Gitea Docker container (memory + repo storage).
- A registry of Rivet Kit sub-agent actors it can spawn and call.
3.3 Sub-Agents
Sub-agents are specialized Rivet Kit worker actors owned by a Grow Agent. They are orchestrated by the Grow Agent and execute their workflows through the user's OpenCode Docker.
Examples:
- Coding agent using OpenCode.
- Repo setup agent using the user's Gitea Docker APIs.
- Migration agent.
- Product flow agent.
- Payment/onboarding agent.
- Quest/pathway agent.
- Backend CRUD agent.
- Frontend planning agent.
Each sub-agent has:
- A unique Rivet Kit actor identity.
- A bounded workspace directory inside the parent Grow Agent's OpenCode Docker.
- A bounded set of capabilities.
- A dedicated state object.
- A channel/thread in the frontend.
- Optional backing microservice integration.
Sub-agent execution rule: every workflow that needs code, shell, file edits, or generated artifacts is executed via the parent Grow Agent's OpenCode Docker session — sub-agents do not get their own container. The Grow Agent multiplexes OpenCode sessions across its sub-agents.
3.4 Git-Backed State
Every user gets a Git repository that stores:
- Agent memory files.
- User goals and profile context.
- Quest/pathway progress.
- Plans, summaries, decisions, and task history.
- Generated code/files.
- Sub-agent outputs.
- System state snapshots where appropriate.
Gitea is used as the internal Git server, and each Grow Agent runs its own Gitea Docker container so per-user repos are physically isolated.
Repository model:
- One Gitea Docker container per Grow Agent (per user).
- One primary repo inside that Gitea for Grow Agent memory and workspace state.
- Optional child repos inside the same Gitea for generated products or user projects.
- All writes from agents go through controlled Git actions against the user's own Gitea Docker.
- Important state mutations produce commits with structured messages.
3.5 OpenCode Execution
OpenCode is used as the code execution and workflow-runtime interface for every sub-agent.
Topology:
- Each Grow Agent owns its own OpenCode Docker container (one container per user).
- All sub-agent workflows are routed through that OpenCode Docker — it is the single execution surface for the Grow Agent's sub-agents.
- OpenCode runs with strict directory boundaries scoped to the user's workspace.
- The Grow Agent creates OpenCode sessions per sub-agent task, sends prompts, inspects results, and streams progress.
- The container is started on Grow Agent provisioning and stopped on suspension to control cost.
Open decision (still open):
- Whether to fork OpenCode and add platform-specific management APIs, or wrap the upstream image behind a backend-controlled management layer (suggested direction in §11).
4. System Architecture
4.1 High-Level Components
- Frontend app: Slack-like UI, chat interface, quests/pathways, progress views. Pulls the Rivet Kit React SDK for actor connectivity.
- Backend API: auth, billing, user management, actor registry, OpenCode Docker lifecycle, Gitea Docker lifecycle.
- Rivet Kit actor runtime: durable Grow Agent and sub-agent actors.
- Per-user Gitea Docker: one container per Grow Agent, hosting that user's repos.
- Per-user OpenCode Docker: one container per Grow Agent, executing all sub-agent workflows.
- Docker orchestration layer: provisions, starts, stops, and tears down each user's OpenCode + Gitea container pair.
- Database: relational app data such as users, auth, billing, actor registry metadata, repo mappings, and container/host assignments.
- Queue/event layer: optional event delivery between backend, actors, OpenCode, and frontend.
Per-user Docker pair (the "Grow Agent stack"):
Frontend ──(Rivet Kit React SDK)──▶ Grow Agent Actor (Rivet Kit)
│
orchestrates sub-agent actors
│
▼
┌──────── User N's stack ────────┐
│ OpenCode Docker ◀── workflows│
│ Gitea Docker ◀── commits │
└────────────────────────────────┘
4.2 Request Flow
- User signs up or logs in.
- Payment or plan check confirms entitlement.
- Backend provisions the user's Grow Agent Rivet Kit actor.
- Backend starts the user's Gitea Docker container and creates the primary memory repo.
- Backend starts the user's OpenCode Docker container and mounts its workspace.
- User sends a message in the frontend (via Rivet Kit React SDK).
- Message is routed to the user's Grow Agent actor.
- Grow Agent updates state, decides whether to spawn/call sub-agent actors, and commits durable context to the user's Gitea Docker when needed.
- Sub-agents run tasks by opening sessions against the user's OpenCode Docker — all workflows flow through this container.
- Progress events stream back to the frontend over the Rivet Kit connection.
5. Backend Requirements
5.1 Auth
The backend must support:
- User registration and login.
- Session or JWT auth.
- Per-user authorization checks for all actor, repo, and OpenCode resources.
- Service-to-service auth for actors calling backend APIs.
Open decision:
- Auth provider: custom auth, Auth.js/NextAuth, Clerk, Supabase Auth, or another provider.
5.2 Actor Registry API
The backend needs an actor registry that tracks:
- User ID.
- Grow Agent actor ID.
- Sub-agent actor IDs.
- Actor type.
- Actor status.
- Assigned workspace path.
- Assigned Gitea repo.
- Assigned OpenCode server/workspace.
- Last activity timestamp.
- Billing entitlement status.
Initial endpoints:
POST /actors/provisionGET /actors/meGET /actors/:actorIdPOST /actors/:actorId/startPOST /actors/:actorId/stopPOST /actors/:actorId/messageGET /actors/:actorId/events
5.3 OpenCode Docker Management API
The backend needs APIs to manage each user's OpenCode Docker container:
- Provision OpenCode Docker container for a Grow Agent.
- Start/stop the OpenCode Docker runtime.
- Create coding/workflow sessions inside the container.
- Send prompt/action to OpenCode.
- Read execution status.
- Fetch logs.
- Restrict filesystem access to the user's workspace mount.
Initial endpoints:
POST /opencode/provisionGET /opencode/workspaces/:workspaceIdPOST /opencode/workspaces/:workspaceId/startPOST /opencode/workspaces/:workspaceId/stopPOST /opencode/workspaces/:workspaceId/sessionsPOST /opencode/sessions/:sessionId/messagesGET /opencode/sessions/:sessionId/events
5.4 Gitea Docker Management API
The backend needs APIs for the per-user Gitea Docker container:
- Provisioning, starting, and stopping the user's Gitea Docker container.
- Creating the primary per-user memory repo inside it.
- Creating additional project repos inside the same Gitea.
- Creating deploy keys or access tokens.
- Committing memory/state files.
- Reading repository status.
- Managing branches.
- Creating PRs when needed.
Initial endpoints:
POST /git/users/:userId/repoGET /git/repos/:repoIdPOST /git/repos/:repoId/commitPOST /git/repos/:repoId/branchPOST /git/repos/:repoId/pull-request
5.5 Payments
Payment controls whether the user's Grow Agent can be provisioned or run.
Requirements:
- Checkout flow.
- Webhook handling.
- Subscription status.
- Entitlement checks before actor startup.
- Graceful suspension when payment fails.
Open decision:
- Payment provider, likely Stripe.
6. Actor Requirements
6.1 Grow Agent Actor
State:
- User profile summary.
- Active goals.
- Current quest/pathway.
- Memory index.
- Sub-agent registry.
- Active tasks.
- Git repo mapping.
- OpenCode workspace mapping.
- Recent conversation summary.
Actions:
- Receive user message.
- Update memory.
- Start quest/pathway.
- Spawn or call sub-agent.
- Commit state to Git.
- Request OpenCode session.
- Emit progress event.
6.2 Sub-Agent Actor
State:
- Parent Grow Agent ID.
- Task type.
- Current task status.
- Workspace path.
- Tool permissions.
- Channel ID.
- Logs/progress.
Actions:
- Start task.
- Pause/resume task.
- Run bounded service action.
- Run OpenCode action where allowed.
- Commit output to Git.
- Emit progress event.
7. Frontend Requirements
The frontend is next, but the backend should be shaped around this UI. The frontend is pulled in as a separate app that consumes the Rivet Kit React/JS SDK to connect directly to the user's Grow Agent actor (chat + streaming events), and uses the backend REST APIs only for auth, billing, and Docker lifecycle controls.
Primary screens:
- Master Grow Agent chat.
- Slack-like channel list.
- Sub-agent channel/thread view.
- Quest/pathway launcher.
- Task progress timeline.
- Files/repo activity view.
- Billing/account state.
UI behavior:
- User talks primarily to the Grow Agent.
- Grow Agent messages can show spawned sub-agent activity.
- Each sub-agent gets a visible channel or thread.
- Quests/pathways appear as predefined flows that trigger agent prompts and actions.
8. Security and Isolation
Hard requirements:
- Every user must have isolated directories.
- Actors can only access assigned workspace roots.
- OpenCode Docker must run with strict workspace and command restrictions, and each user's container is network-isolated from other users' containers.
- Each user's Gitea Docker is reachable only from that user's Grow Agent + sub-agents and the backend.
- Backend must verify user ownership on every actor, repo, and OpenCode request.
- Sub-agents should receive only the capabilities needed for their task.
- Per-user OpenCode and Gitea Docker containers must have CPU/memory limits to prevent noisy-neighbor and runaway-cost issues.
9. MVP Scope
MVP Backend
- User auth.
- Actor registry.
- One Grow Agent Rivet Kit actor per user.
- Basic sub-agent (Rivet Kit) registration under the Grow Agent.
- Per-user Gitea Docker provisioning and primary repo creation.
- Basic Git-backed memory commits into the user's Gitea Docker.
- Per-user OpenCode Docker provisioning + session API.
- Message endpoint from frontend to Grow Agent.
- Event stream endpoint for progress.
MVP Frontend
- Pulled as a separate app that consumes the Rivet Kit React SDK.
- Login.
- Master chat interface (Rivet Kit actor connection to the Grow Agent).
- Sub-agent progress sidebar.
- Basic quest launcher.
- Channel-style task logs.
MVP Actors
- Grow Agent actor with memory and routing.
- Coding sub-agent using OpenCode.
- Repo sub-agent using Gitea.
- Quest sub-agent using predefined prompts.
10. Key Open Questions
Resolved:
Should there be one OpenCode container per user or per active coding sub-agent?→ One OpenCode Docker container per Grow Agent (per user). Sub-agents share it via separate sessions.Gitea topology?→ One Gitea Docker container per Grow Agent (per user).Actor framework?→ Rivet Kit for both Grow Agent and sub-agents.How does the frontend connect to actors?→ Frontend pulls and uses the Rivet Kit React/JS SDK.
Still open:
- Should OpenCode be forked, wrapped, or used as-is behind a management API?
- Should the user memory repo and generated product repos be separate (both inside the same per-user Gitea)?
- Which auth provider should be used?
- Which database should be used for backend metadata?
- How much state should live in Rivet actors versus Git versus database?
- Should sub-agent channels map to real Slack channels, an internal Slack-like UI, or both?
- What is the exact boundary between a sub-agent actor and a microservice wrapper?
- What payment provider and pricing model should be used?
- Which Docker orchestrator runs the per-user OpenCode + Gitea pair (plain Docker, Docker Compose per user, Nomad, k8s, Fly Machines, etc.)?
11. Suggested Technical Direction
- Use the backend database for account, billing, registry, and resource mappings (including per-user OpenCode/Gitea container IDs and hosts).
- Use Rivet Kit actors for durable runtime state and orchestration; the Grow Agent is the orchestrator actor and sub-agents are child actors.
- Use Git/Gitea (per-user Docker) for long-term memory, files, project artifacts, and auditable history.
- Use a per-user OpenCode Docker behind a backend-controlled management layer; sub-agent workflows execute via OpenCode sessions, not by spawning their own containers.
- Pull the frontend as a separate app that consumes the Rivet Kit React SDK for actor traffic and the backend REST API for control plane.
- Start with an internal Slack-like frontend channel model before integrating real Slack.
- Avoid forking OpenCode until the wrapper approach proves insufficient.