Codev OpenCode PVC Implementation - Session Recovery

Date: 2026-02-05
PR: https://github.com/craigedmunds/k8s-lab/pull/23
Status: PR created, awaiting merge for ArgoCD sync

Context

We implemented Story 1.5 (OpenCode State Persistence) and Story 1.6 (Plugin Auto-Discovery) for the codev component in k8s-lab. The implementation includes:

  1. PVC Mount: OpenCode state persists on dedicated PVC at /home/coder/.local
  2. Plugin Auto-Init: Bridge plugin loads from stable ai-dev repo at /home/coder/src/repos/ai-dev/plugins/opencode-bridge
  3. Acceptance Tests: Comprehensive test suite using kubectl exec to probe running container

Current State

✅ Completed

  • Updated start-af.sh with plugin auto-initialization logic
  • Updated PLUGIN-LOADING.md documentation
  • Created test_pvc_acceptance.py with 11 acceptance criteria tests
  • Committed changes to branch feat/opencode-plugin-auto-init
  • Pushed to GitHub
  • Created PR #23

⏳ Pending

  • PR review and merge
  • ArgoCD auto-sync (deploys updated codev deployment)
  • Run acceptance tests to verify all 11 ACs pass

Key Decisions Made

Plugin Source Location

Decision: Use single source at /home/coder/src/repos/ai-dev/plugins/opencode-bridge

Rationale:

  • ✅ Stable code from main branch (merged, reviewed)
  • ✅ Isolated from active AI dev work in builder workspaces
  • ✅ Predictable - updates only when repo is pulled
  • ✅ Simple - no confusing priority logic

Rejected Alternatives:

  • .opencode-plugins/ override directory (adds complexity)
  • ❌ Builder workspace sources (unstable, WIP code)
  • ❌ Multiple location priority (confusing, error-prone)

PVC Mount Point

Current: /home/coder/.local (per deployment.yaml)
Running Deployment: /home/coder/.local/share/opencode (old, will update after merge)

Files Modified

k8s-lab/components/remote-development/codev/
├── start-af.sh               (47 lines of auto-init logic)
├── PLUGIN-LOADING.md         (updated docs, removed overrides)
└── test_pvc_acceptance.py    (NEW: 400+ lines, 11 ACs)

Next Steps

Immediate (After PR Merge)

# 1. Wait for ArgoCD to sync (auto-detects merged PR)
# Monitor: ArgoCD UI or kubectl
 
# 2. Verify pod restarted with new image
kubectl get pods -n code-server -l app=codev
 
# 3. Check logs for plugin initialization
kubectl logs -n code-server deployment/codev | grep -E "plugin|Bridge"
 
# Expected output:
# 🔌 Checking for OpenCode bridge plugin...
# ✅ Found plugin at: /home/coder/src/repos/ai-dev/plugins/opencode-bridge
# 🔧 Setting up OpenCode bridge plugin...
# ✅ Bridge plugin configured and ready
 
# 4. Run acceptance tests
cd /home/coder/src/repos/k8s-lab/components/remote-development/codev
python3 test_pvc_acceptance.py
 
# Expected: All 11 ACs pass

If Session Lost (Paste This Prompt)

I was working on implementing OpenCode PVC persistence and plugin auto-initialization for the codev component in k8s-lab.

**Current Status**:
- PR #23 created: https://github.com/craigedmunds/k8s-lab/pull/23
- Branch: feat/opencode-plugin-auto-init
- Files modified: start-af.sh, PLUGIN-LOADING.md, test_pvc_acceptance.py (new)

**What I need**:
1. Check if PR #23 has been merged
2. If merged: Verify ArgoCD synced the codev deployment
3. Run acceptance tests: `cd /home/coder/src/repos/k8s-lab/components/remote-development/codev && python3 test_pvc_acceptance.py`
4. Verify all 11 acceptance criteria pass (Stories 1.5 & 1.6)

**Key Implementation Details**:
- Plugin loads from: /home/coder/src/repos/ai-dev/plugins/opencode-bridge (single source, stable repo)
- PVC mount: /home/coder/.local (for OpenCode state persistence)
- Auto-init on pod startup: checks for plugin, installs deps, builds, symlinks
- Graceful degradation: pod starts even without plugin

**If tests fail**:
- Check pod logs: `kubectl logs -n code-server deployment/codev | grep -E "plugin|Bridge"`
- Verify plugin source exists: `kubectl exec -n code-server deployment/codev -- ls -la /home/coder/src/repos/ai-dev/plugins/opencode-bridge`
- Check PVC mount: `kubectl exec -n code-server deployment/codev -- df /home/coder/.local`

**Context**: This implements Story 1.5 (OpenCode State Persistence via PVC) and Story 1.6 (Plugin Auto-Discovery and Initialization) from the OpenCode Slack Integration epic.

Acceptance Criteria

Story 1.5: OpenCode State Persistence via PVC

  • AC1: PVC mounted at /home/coder/.local
  • AC2: Auth tokens persist in auth.json
  • AC3: Session metadata persists in storage/session/
  • AC4: Message history persists
  • AC5: PVC mount configuration correct

Story 1.6: Plugin Auto-Discovery and Initialization

  • AC1: Plugin auto-discovered from /home/coder/src/repos/ai-dev/plugins/opencode-bridge
  • AC2: Plugin symlinked to ~/.config/opencode/node_modules/@opencode/bridge-plugin
  • AC3: Plugin on PVC (no Docker rebuild needed)
  • AC4: npm dependencies auto-installed
  • AC5: Graceful degradation (pod runs without plugin)
  • AC6: Plugin auto-built if dist/ missing

Troubleshooting

Plugin Not Loading

# Check if plugin exists
kubectl exec -n code-server deployment/codev -- \
  test -d /home/coder/src/repos/ai-dev/plugins/opencode-bridge && echo "exists" || echo "missing"
 
# Check if ai-dev repo is checked out
kubectl exec -n code-server deployment/codev -- \
  ls -la /home/coder/src/repos/ | grep ai-dev
 
# If missing, clone repo
kubectl exec -n code-server deployment/codev -- \
  git clone https://github.com/craigedmunds/ai-dev.git /home/coder/src/repos/ai-dev

PVC Mount Issues

# Check PVC status
kubectl get pvc -n code-server opencode-state
 
# Check mount in pod
kubectl exec -n code-server deployment/codev -- \
  df -h /home/coder/.local
 
# Check OpenCode state data
kubectl exec -n code-server deployment/codev -- \
  du -sh /home/coder/.local/share/opencode

Tests Fail

# Ensure kubectl can reach cluster
kubectl get pods -n code-server
 
# Ensure codev pod is running
kubectl get pods -n code-server -l app=codev
 
# Check pod logs for errors
kubectl logs -n code-server deployment/codev --tail=100
 
# Re-run specific test sections
cd /home/coder/src/repos/k8s-lab/components/remote-development/codev
python3 test_pvc_acceptance.py 2>&1 | grep -A 5 "Story 1.6"
  • Epic: .ai/projects/ai-dev/opencode-slack-integration/epics.md
  • Plugin Docs: k8s-lab/components/remote-development/codev/PLUGIN-LOADING.md
  • Tests: k8s-lab/components/remote-development/codev/test_pvc_acceptance.py
  • Deployment: k8s-lab/components/remote-development/codev/deployment.yaml

Success Criteria

✅ PR merged
✅ ArgoCD synced deployment
✅ Pod restarted with new init script
✅ Plugin auto-discovered and initialized
✅ All 11 acceptance tests pass
✅ OpenCode state persisting on PVC

Notes

  • The running deployment currently has old mount path (/home/coder/.local/share/opencode)
  • This will be corrected when ArgoCD syncs the deployment after PR merge
  • Tests enforce correct configuration (no backwards compatibility)
  • Plugin source must be from stable ai-dev repo (no overrides)