Portal API
All portal endpoints require a valid friend session token via Authorization: Bearer <token>.
Profile
Section titled “Profile” GET /api/portal/me friend
Get the current friend's profile, display name, namespace, and stats (log count, secret count).
Response:
{ "id": "alice", "display_name": "Alice", "preferred_channel": "signal", "namespace": "friend-alice", "stats": { "logs": 42, "secrets": 3 }}Agent Relationships
Section titled “Agent Relationships” GET /api/portal/agents friend
List agent relationships for the current friend (from friendships table).
Namespace Overview
Section titled “Namespace Overview” GET /api/portal/namespace friend
Full namespace overview: pods, services, deployments, quota, and IngressRoutes.
Response:
{ "pods": [...], "services": [...], "deployments": [ { "name": "my-app", "replicas": "1/1", "image": "nginx:alpine", "age": "2026-03-01T10:00:00Z", "secretRefs": ["my-api-key"] } ], "quota": {...}, "ingressRoutes": [ {"name": "expose-my-app", "hostname": "my-app-alice.your-domain.net", "service": "my-app"} ]}Available Domains
Section titled “Available Domains” GET /api/portal/domains friend
List available domains for service exposure.
Service Exposure
Section titled “Service Exposure” POST /api/portal/namespace/expose friend
Expose a service publicly. Creates IngressRoute + DNS record. Name must be alphanumeric + hyphens, 1-20 chars.
Body:
{ "name": "my-app", "service": "my-app", "port": 80, "domain": "your-domain.net"} DELETE /api/portal/namespace/expose/:name friend
Remove a service exposure. Deletes IngressRoute and DNS record.
Workspace Memory
Section titled “Workspace Memory” GET /api/portal/workspace/memory friend
Read the friend's editable MEMORY.md file.
Response:
{ "content": "# My Notes\n\nRemember to ask the agent about...", "exists": true} PUT /api/portal/workspace/memory friend
Update the friend's MEMORY.md file.
Body:
{"content": "# Updated Notes\n\n..."} GET /api/portal/workspace/friend-notes friend
Read the agent's notes about you (read-only).
Heartbeat
Section titled “Heartbeat” GET /api/portal/workspace/heartbeat friend
Read the agent's HEARTBEAT.md scheduler config.
PUT /api/portal/workspace/heartbeat friend
Update the HEARTBEAT.md config.
Cron Jobs
Section titled “Cron Jobs” GET /api/portal/workspace/crons friend
List cron jobs targeting the current friend's sessions.
POST /api/portal/workspace/crons friend
Create a new cron job. Must target the friend's own session or contact.
Body:
{ "name": "daily-check", "message": "Check my portfolio", "cron": "0 9 * * *", "session": "agent:main:direct:channel:alice", "tz": "Europe/Berlin"} DELETE /api/portal/workspace/crons/:name friend
Delete a cron job (must be owned by the friend).
POST /api/portal/workspace/crons/:name/run friend
Manually trigger a cron job.
POST /api/portal/workspace/crons/:name/toggle friend
Enable or disable a cron job.
Body:
{"enabled": true}