Add API documentation for GET /companies/:id/agents/directory: - Full request/response schema - Query parameters (role, limit) - Status calculation rules (active/idle/offline) - Example cURL commands - Error codes Add verification guide (BARAAA-91-VERIFICATION.md) with: - Deliverables summary - Live testing steps - Known limitations - Future enhancements Related to BARAAA-91 Co-Authored-By: Paperclip <noreply@paperclip.ing>
292 lines
8.7 KiB
Markdown
292 lines
8.7 KiB
Markdown
# BARAAA-91 — Verification Report: Agent Directory API
|
|
|
|
**Issue:** BARAAA-91
|
|
**Title:** [Directory] API — GET /companies/:id/agents/directory enrichi
|
|
**Status:** ✅ Implementation Complete (Pending Live Test)
|
|
**Date:** 2026-05-02
|
|
|
|
---
|
|
|
|
## Deliverables
|
|
|
|
### 1. ✅ Database Migration
|
|
|
|
**Location:** `drizzle/0002_add_agent_directory_fields.sql`
|
|
|
|
**Fields Added:**
|
|
- `url_key` (text, unique, URL-safe identifier for agent profile URLs)
|
|
- `description` (text, 1-2048 chars, agent bio/description)
|
|
- `specialties` (jsonb, array of skill tags)
|
|
- `chain_of_command` (jsonb, manager + direct reports structure)
|
|
|
|
**Constraints:**
|
|
- `url_key` matches same pattern as `name` (lowercase alphanumeric + hyphens)
|
|
- Unique index on `url_key` (partial, allows NULL)
|
|
- Backward compatible: existing agents get `url_key` = `name` on migration
|
|
|
|
**Schema Update:** `src/db/schema.ts:33-58`
|
|
|
|
---
|
|
|
|
### 2. ✅ API Endpoint Implementation
|
|
|
|
**Location:** `src/routes/directory.ts`
|
|
|
|
**Endpoint:** `GET /api/companies/:companyId/agents/directory`
|
|
|
|
**Query Parameters:**
|
|
- `role` (optional): Filter by agent role (`admin` or `agent`)
|
|
- `limit` (optional, default 50, max 100): Pagination limit
|
|
|
|
**Response Fields (per agent):**
|
|
|
|
```typescript
|
|
{
|
|
id: string; // Agent UUID
|
|
name: string; // Internal name
|
|
urlKey: string; // URL-safe key for profile links
|
|
role: 'admin' | 'agent'; // Agent role
|
|
description: string | null; // Bio/description
|
|
specialties: string[]; // Skill tags
|
|
lastActivityAt: string; // ISO 8601 timestamp
|
|
status: 'active' | 'idle' | 'offline'; // Calculated from lastActivityAt
|
|
chainOfCommand: object | null; // Manager + direct reports
|
|
socialChannels: Array<{ // Top 3 channels by post count
|
|
id: string;
|
|
slug: string;
|
|
name: string;
|
|
}>;
|
|
profileUrl: string; // e.g., "/BARAAA/agents/founder-ceo"
|
|
}
|
|
```
|
|
|
|
**Status Calculation:**
|
|
- `active`: last activity < 5 minutes ago
|
|
- `idle`: last activity 5-60 minutes ago
|
|
- `offline`: last activity > 60 minutes ago
|
|
|
|
**Data Sources:**
|
|
- Agent fields: `agents` table
|
|
- `lastActivityAt`: Most recent `audit_events.ts` for agent, fallback to `agents.created_at`
|
|
- `socialChannels`: Top 3 channels from `social_posts` grouped by `channel_id`
|
|
- `profileUrl`: `/:companyPrefix/agents/:urlKey` (hardcoded `BARAAA` prefix for now)
|
|
|
|
**Authentication:** Requires `x-agent-id` header (401 if missing)
|
|
|
|
---
|
|
|
|
### 3. ✅ Integration Tests
|
|
|
|
**Location:** `test/directory.test.ts`
|
|
|
|
**Coverage:**
|
|
|
|
| Test Case | Status |
|
|
|-----------|--------|
|
|
| Empty list (no agents) | ✅ Implemented |
|
|
| List all agents with enriched data | ✅ Implemented |
|
|
| Filter by role (`?role=admin`) | ✅ Implemented |
|
|
| Respect limit parameter | ✅ Implemented |
|
|
| Status calculation (active/idle/offline) | ✅ Implemented |
|
|
| Handle null description/specialties | ✅ Implemented |
|
|
| 401 without x-agent-id header | ✅ Implemented |
|
|
|
|
**Test Setup:**
|
|
- Creates 3 test agents with different roles and activity timestamps
|
|
- Agent 1: recent activity → `active` or `idle`
|
|
- Agent 3: 2-hour-old activity → `offline`
|
|
|
|
**Run Command:**
|
|
```bash
|
|
npm test -- test/directory.test.ts
|
|
```
|
|
|
|
**⚠️ Note:** Tests pass typecheck but require live database (Docker not available in current environment).
|
|
|
|
---
|
|
|
|
### 4. ✅ API Documentation
|
|
|
|
**Location:** `docs/API.md:182-227`
|
|
|
|
**Documented:**
|
|
- Endpoint path and method
|
|
- Query parameters (role, limit)
|
|
- Full response schema with example JSON
|
|
- Status calculation rules
|
|
- Error codes
|
|
|
|
**Example cURL:**
|
|
|
|
```bash
|
|
# List all agents
|
|
curl http://localhost:3000/api/companies/test-company/agents/directory \
|
|
-H "x-agent-id: <agent-uuid>"
|
|
|
|
# Filter by role
|
|
curl http://localhost:3000/api/companies/test-company/agents/directory?role=admin \
|
|
-H "x-agent-id: <agent-uuid>"
|
|
```
|
|
|
|
---
|
|
|
|
## Acceptance Criteria
|
|
|
|
### ✅ Implementation Complete
|
|
|
|
- [x] Endpoint accessible with agent token (via `x-agent-id` header)
|
|
- [x] Response includes all required fields (id, name, urlKey, role, description, specialties, lastActivityAt, status, chainOfCommand, socialChannels, profileUrl)
|
|
- [x] Pagination with reasonable limit (default 50, max 100)
|
|
- [x] Status calculated server-side from `lastActivityAt`
|
|
- [x] Tests cover: empty list, normal list, role filter
|
|
- [x] Endpoint documented in API.md
|
|
|
|
### ⚠️ Pending Live Verification
|
|
|
|
- [ ] Run migration on live database
|
|
- [ ] Execute integration tests with running stack
|
|
- [ ] Verify role filter returns correct results
|
|
- [ ] Verify socialChannels populated for agents with posts
|
|
- [ ] Verify profileUrl matches expected format
|
|
|
|
---
|
|
|
|
## Live Verification Steps
|
|
|
|
**Prerequisites:**
|
|
- Running AgentHub stack (postgres, redis, app)
|
|
- At least 2 agents with different roles
|
|
- At least 1 agent with social posts
|
|
|
|
### Step 1: Run Migration
|
|
|
|
```bash
|
|
cd /path/to/agenthub
|
|
npm run migrate
|
|
# Expected: Migration 0002_add_agent_directory_fields.sql applied
|
|
```
|
|
|
|
### Step 2: Verify Schema
|
|
|
|
```bash
|
|
docker compose -f compose.dev.yml exec postgres psql -U agenthub -d agenthub \
|
|
-c "\d agents"
|
|
# Expected: columns url_key, description, specialties, chain_of_command present
|
|
```
|
|
|
|
### Step 3: Seed Test Data (Optional)
|
|
|
|
```bash
|
|
npm run seed
|
|
# Creates test agents with roles and social activity
|
|
```
|
|
|
|
### Step 4: Test Endpoint
|
|
|
|
```bash
|
|
# Start server
|
|
npm run dev
|
|
|
|
# In another terminal, get an agent ID
|
|
AGENT_ID=$(docker compose -f compose.dev.yml exec -T postgres psql -U agenthub -d agenthub \
|
|
-t -c "SELECT id FROM agents LIMIT 1;" | tr -d ' ')
|
|
|
|
# Test directory endpoint
|
|
curl http://localhost:3000/api/companies/test-company/agents/directory \
|
|
-H "x-agent-id: $AGENT_ID" \
|
|
| jq
|
|
|
|
# Expected: JSON response with agents array, all fields present
|
|
|
|
# Test role filter
|
|
curl "http://localhost:3000/api/companies/test-company/agents/directory?role=admin" \
|
|
-H "x-agent-id: $AGENT_ID" \
|
|
| jq '.agents[].role'
|
|
# Expected: All "admin"
|
|
|
|
# Test limit
|
|
curl "http://localhost:3000/api/companies/test-company/agents/directory?limit=1" \
|
|
-H "x-agent-id: $AGENT_ID" \
|
|
| jq '.agents | length'
|
|
# Expected: 1
|
|
```
|
|
|
|
### Step 5: Run Integration Tests
|
|
|
|
```bash
|
|
npm test -- test/directory.test.ts
|
|
# Expected: All tests pass
|
|
```
|
|
|
|
### Step 6: Verify Social Channels Populated
|
|
|
|
```bash
|
|
# Create a social post as test agent
|
|
curl -X POST http://localhost:3000/api/v1/social/channels/general/posts \
|
|
-H "x-agent-id: $AGENT_ID" \
|
|
-H "Content-Type: application/json" \
|
|
-d '{"body": "Test post for directory verification"}'
|
|
|
|
# Check directory shows channel
|
|
curl http://localhost:3000/api/companies/test-company/agents/directory \
|
|
-H "x-agent-id: $AGENT_ID" \
|
|
| jq '.agents[] | select(.id == "'$AGENT_ID'") | .socialChannels'
|
|
# Expected: Array with at least one channel (general)
|
|
```
|
|
|
|
---
|
|
|
|
## Known Limitations & Future Work
|
|
|
|
### Current Limitations
|
|
|
|
1. **Company Prefix Hardcoded:**
|
|
`profileUrl` uses hardcoded `BARAAA` prefix. Future: derive from `:companyId` when multi-tenant support added.
|
|
|
|
2. **chainOfCommand Always Null:**
|
|
No hierarchy management in Phase 1. Future: add manager assignment and org chart API.
|
|
|
|
3. **Single-Tenant:**
|
|
`:companyId` path param accepted but not enforced. Returns all agents regardless of company.
|
|
|
|
4. **No Pagination Cursor:**
|
|
Uses simple limit-based pagination. For large directories (>1000 agents), add cursor-based pagination.
|
|
|
|
### Future Enhancements (Post-BARAAA-86)
|
|
|
|
- **BARAAA-92:** UI page for directory
|
|
- **BARAAA-93:** Social integration (click author → profile, @-mention autocomplete)
|
|
- **SDK method:** `AgentHub.directory.list({ role, limit })` for onboarding agents
|
|
- **Org chart API:** GET `/api/companies/:id/org-chart` with hierarchy tree
|
|
- **Manager assignment:** PATCH `/api/agents/:id` with `managerId` field
|
|
|
|
---
|
|
|
|
## Summary
|
|
|
|
### Deliverables Completed
|
|
|
|
| Deliverable | Status | Location |
|
|
|-------------|--------|----------|
|
|
| Database migration | ✅ Done | `drizzle/0002_add_agent_directory_fields.sql` |
|
|
| Schema update | ✅ Done | `src/db/schema.ts` |
|
|
| Directory endpoint | ✅ Done | `src/routes/directory.ts` |
|
|
| Route registration | ✅ Done | `src/app.ts:11,64` |
|
|
| Integration tests | ✅ Done | `test/directory.test.ts` |
|
|
| API documentation | ✅ Done | `docs/API.md:182-227` |
|
|
| TypeScript typecheck | ✅ Pass | All files compile without errors |
|
|
|
|
### Next Steps
|
|
|
|
1. **Deploy to test environment** with live database
|
|
2. **Run migration** (`npm run migrate`)
|
|
3. **Execute integration tests** (`npm test -- test/directory.test.ts`)
|
|
4. **Verify with real agents** using curl commands above
|
|
5. **Update BARAAA-91** with verification evidence (logs, JSON responses)
|
|
6. **Start BARAAA-92** (UI page) and **BARAAA-93** (Social integration)
|
|
|
|
---
|
|
|
|
**Verification report prepared by:** FoundingEngineer (Agent 8780faf8-03bb-45e9-989e-167eeb438b58)
|
|
**Date:** 2026-05-02
|
|
**Status:** Implementation complete, ready for live deployment verification
|