144 Work Report

Documentation for Sessions

Session 144 — Work Summary (February 26, 2026)

What Was Done

Session 144 closed 4 "gaps" from the Vitto Super-Agent roadmap (Gaps 9-12). Here's what each one means in plain English.


Gap 12 — A2A Protocol Tests (DONE)

What is A2A? Google's Agent-to-Agent protocol — a standard way for AI agents to discover each other and send tasks. We already had a working A2A implementation in backend-vitto-api. What was missing: tests.

What was built: 5 test files covering every public method:

Location: APIs/backend-vitto-api/src/app/a2a/__tests__/

Status: Complete. Zero production code changed — tests only.


Gap 10 — Sandbox Provider Abstraction (DONE)

The problem: Our Computer Use system (where an AI controls a browser/desktop) was hardcoded to use E2B Cloud. If we wanted to use our own servers instead, we'd have to rewrite the entire loop.

What was built: A Strategy pattern that lets us swap sandbox providers without touching the core logic.

ComputerUseLoopService
    -> SandboxProviderFactory (picks the right one automatically)
            |-- E2BCloudProvider    <- wraps existing E2B Desktop SDK
            |-- SelfHostedProvider  <- HTTP client for our future server
            |-- PlaywrightProvider  <- local browser fallback

How it picks a provider (env vars):

  1. If SANDBOX_SERVER_URL is set -> SelfHostedProvider
  2. If E2B_API_KEY is set -> E2BCloudProvider (this is what we use today)
  3. Neither -> PlaywrightProvider (free, local, limited)

What changed in the codebase:

Location: APIs/backend-ai-api/src/app/infrastructure/services/sandbox/

Status: Complete. E2B Cloud works exactly as before. Self-hosted provider is scaffolded (HTTP client code exists, but there's no server to connect to yet — see Gaps section below).


Gap 11 — Observability Dashboard (DONE)

The problem: We had no unified view of system health. Each backend had its own /health endpoint, but nothing aggregated them or tracked LLM spending.

What was built:

Backend (3 new files)

  1. LLM Cost Tracker (llm-cost-tracker.service.ts)

    • Records every LLM API call: model, tokens in/out, cost, user
    • Rolling 24-hour window (in-memory, no database overhead)
    • Model-specific pricing (Claude Opus 4.6: $15/$75 per 1M tokens, etc.)
    • Called automatically after every Anthropic API call in Computer Use
  2. Observatory Service (observatory.service.ts)

    • Checks health of all 4 backends every 30 seconds (cached)
    • Aggregates into a single dashboard JSON
    • Also generates Prometheus-format text metrics
  3. Observatory Controller (observatory.controller.ts)

    • GET /infrastructure/observatory/dashboard — full dashboard JSON
    • GET /infrastructure/observatory/metrics — Prometheus text format
    • GET /infrastructure/observatory/llm-spend — 24h token summary
    • GET /infrastructure/observatory/llm-daily — daily cost history

Frontend (4 new files)

  1. Observatory Data Service — Angular service that polls the dashboard endpoint
  2. Observatory Dashboard Component — Shows backend health cards, LLM spend breakdown, agent/system metrics
  3. Observatory Page updated with tab system: "Agent Monitor" (existing) + "System Dashboard" (new)

Location:

Status: Complete. Navigate to /observatory and click "System Dashboard" tab.


Gap 9 — Vitto Mobile App (SCAFFOLDED)

What is it? A native mobile wrapper around our existing Angular app, exactly like vitto-desktop wraps it with Tauri — but using Capacitor for iOS/Android instead.

What exists today

Item Status
apps/vitto-mobile/capacitor.config.ts Created
apps/vitto-mobile/project.json (NX targets) Created
apps/vitto-mobile/package.json (metadata) Created
CapacitorBridgeService (Angular service) Created
Auth guard mobile detection Added
App initializer hook Added
ios/ native directory Not created
android/ native directory Not created
Capacitor npm dependencies installed No
CI/CD pipeline No
Tested on device/simulator No

Tech Stack

How it works (same pattern as Tauri desktop)

Angular App (gograb-ai)
    |-- Tauri wrapper   -> Vitto Desktop (macOS/Windows/Linux)
    |-- Capacitor wrapper -> Vitto Mobile (iOS/Android)  <- NEW

The Angular app builds once. Both wrappers load the same dist/ output. Each wrapper provides native capabilities through a bridge service (TauriBridgeService for desktop, CapacitorBridgeService for mobile). Both services are no-ops when running in a regular browser.

Is it ready to use?

No. It's a scaffolding — the NX project and configuration exist, but you can't run cap sync or open it in Xcode/Android Studio yet because:

  1. Capacitor packages aren't installed in root package.json
  2. No npx cap add ios / npx cap add android has been run
  3. No native directories exist
  4. No signing certificates configured

What's needed to make it work

# 1. Install Capacitor
yarn add @capacitor/core @capacitor/ios @capacitor/android
yarn add -D @capacitor/cli

# 2. Install plugins
yarn add @capacitor/push-notifications @capacitor/haptics \
         @capacitor/splash-screen @capacitor/status-bar @capacitor/browser

# 3. Build Angular app
nx build app-gograb-ai

# 4. Add native platforms
cd apps/vitto-mobile
npx cap add ios
npx cap add android
npx cap sync

# 5. Open in IDE
npx cap open ios     # Opens Xcode
npx cap open android # Opens Android Studio

Current State of E2B / Sandbox Infrastructure

What works RIGHT NOW

Component Status Details
E2B Cloud Active E2B_API_KEY is set in .env.local. Firecracker VMs spin up on demand via @e2b/desktop SDK
Playwright fallback Active Used when E2B key is missing or for targetType: 'desktop' goals
Provider abstraction Active SandboxProviderFactory selects provider based on env vars at startup
LLM cost tracking Active Every Computer Use API call now records tokens/cost
Per-session sandboxes Active Each Computer Use session gets its own isolated VM (30min idle, 55min max)

What is SCAFFOLDED (not working yet)

Component Status What's missing
Self-hosted provider HTTP client exists No server to connect to. The SelfHostedProvider will send HTTP requests to SANDBOX_SERVER_URL, but we haven't built the Sandbox Orchestrator server yet
Sandbox Orchestrator Plan document only The 6-phase plan is at docs/english/Plans/self-hosted-e2b.plan.md (420 lines). Zero implementation
Custom Firecracker images Plan only Need Ubuntu rootfs with XFCE, Chrome, x11vnc, xdotool pre-installed
Hetzner server Not provisioned Plan targets AX41-NVMe ($46/mo) with KVM support

In simple terms

We currently pay E2B for cloud VMs. The abstraction layer is done, so when we're ready to run our own VMs, we just:

  1. Build the Sandbox Orchestrator server (NestJS service on Hetzner)
  2. Set SANDBOX_SERVER_URL=https://sandbox.gograb.space in .env.local
  3. The system automatically switches to self-hosted. No changes to the Computer Use loop.

The break-even point is ~10 active users (E2B Pro is $150/mo + usage vs self-hosted at $46/mo fixed).


Files Created This Session

File Purpose
APIs/backend-ai-api/.../sandbox/sandbox-provider.interface.ts SandboxProvider interface + SandboxHandle type
APIs/backend-ai-api/.../sandbox/e2b-cloud.provider.ts Wraps existing E2BDesktopService
APIs/backend-ai-api/.../sandbox/self-hosted.provider.ts HTTP client for future orchestrator
APIs/backend-ai-api/.../sandbox/playwright.provider.ts Wraps BrowserAutomationService
APIs/backend-ai-api/.../sandbox/sandbox-provider.factory.ts Env-based provider selection
APIs/backend-ai-api/.../sandbox/index.ts Barrel export
APIs/backend-ai-api/.../llm-cost-tracker.service.ts In-memory LLM spend tracking
APIs/backend-ai-api/.../observatory.service.ts Health aggregation + Prometheus metrics
APIs/backend-ai-api/.../controllers/observatory.controller.ts 4 REST endpoints
libs/libs-ai/.../observatory-data.service.ts Frontend data service
libs/libs-ai/.../observatory-dashboard/ (3 files) Frontend dashboard component
apps/vitto-mobile/capacitor.config.ts Capacitor configuration
apps/vitto-mobile/project.json NX project with mobile targets
apps/vitto-mobile/package.json Package metadata
apps/gograb-ai/.../capacitor-bridge.service.ts Runtime bridge to Capacitor plugins
APIs/backend-vitto-api/.../a2a/__tests__/ (5 files) A2A protocol integration tests

Files Modified This Session

File Change
computer-use-loop.service.ts Removed E2BDesktopService dependency, added LLM cost tracking
infrastructure.module.ts Registered observatory services and controller
observatory-page.component.* (3 files) Added tab system
desktop-auth.guard.ts Added isMobile check
app.config.ts Added CapacitorBridge initializer
libs/libs-ai/.../components/index.ts Exported ObservatoryDashboardComponent
libs/libs-ai/.../services/index.ts Exported ObservatoryDataService

Remaining Gaps / Next Steps

  1. Self-Hosted Sandbox Orchestrator — The biggest remaining piece. Need to build the NestJS service that runs on Hetzner and manages Firecracker VMs. Plan is written, implementation is zero.

  2. Vitto Mobile -> Real Device — Install Capacitor packages, run cap add ios/android, test on simulator, set up signing and CI/CD.

  3. A2A Tests -> Run them — Tests were written but should be verified with nx test backend-vitto-api --testPathPattern=a2a.

  4. LLM Cost Persistence — Currently in-memory only (resets on server restart). Could add MongoDB persistence for historical trends.

  5. Prometheus Scraping — The /metrics endpoint exists but no Prometheus/Grafana instance is set up to scrape it.