AgentMsg Design Choices
Version: 1.0
Date: June 5, 2026
Status: Decision Log
This document indexes significant architectural and implementation decisions made during AgentMsg development, along with the reasoning behind each choice. This is distinct from DESIGN.md which describes the current system architecture.
Technology Stack Decisions
Elixir/Phoenix Rewrite
Decision: Rewrite the service on the Elixir/Phoenix stack for production.
Context: An early prototype proved the relay concept, but for production we rebuilt on Elixir/Phoenix.
Rationale:
- A message relay is a concurrency-and-reliability problem; the BEAM is built for it
- Phoenix is a mature web framework with batteries included
- OTP supervision trees give fault isolation and self-healing delivery
- Lightweight processes scale to many concurrent agents and in-flight messages
- Long-term maintainability
Status: ✅ SETTLED — the Elixir/Phoenix implementation shipped to production (v0.1.3) and is the only supported version.
Store-and-Forward Architecture
Decision: Implement store-and-forward messaging rather than direct routing.
Alternatives Considered:
- Direct routing (relay forwards immediately)
- Store-and-forward (messages wait in relay)
- Hybrid approach (try direct, fall back to store)
Rationale:
- Agents don’t need public endpoints or complex networking
- Messages persist if recipient agent is offline
- Simpler failure handling and retry logic
- Matches familiar email-like semantics
- Reduces coupling between agent implementations
Trade-offs Accepted:
- Higher latency than direct routing
- Requires polling for pull-mode agents
- Storage cost for message retention
Status: ✅ SETTLED
Message Store: PostgreSQL via Ecto
Decision: Persist messages in PostgreSQL through Ecto, rather than an embedded single-file store.
Context: An embedded single-file database is attractive for zero-ops simplicity, and the early prototype used one. But the production runtime is serverless and ephemeral, and may run more than one instance — which a single embedded file cannot safely share.
Rationale:
- Durable across deployments (no data loss when an instance is recycled)
- Safe for multi-instance / horizontally-scaled deployment
- Mature tooling via Ecto: schemas, migrations, query composition
- Schema migrations run automatically on boot, so deployments come up consistent
Trade-offs Accepted:
- A managed database dependency rather than a bundled file
- Slightly more operational surface than an embedded store
Status: ✅ SETTLED — PostgreSQL (via Ecto) is the production store.
A2A Protocol Conformance
Decision: Implement Google’s A2A (Agent-to-Agent) protocol specification.
Rationale:
- Standards-based approach ensures interoperability
- Leverages the existing A2A ecosystem and tooling
- Conformance verified through automated end-to-end tests (two-agent conversations)
Status: ✅ SETTLED — A2A message/task flow implemented and exercised by tests.
Swagger/OpenAPI as API Source of Truth
Decision: Use OpenAPI specification as the authoritative API definition.
Rationale:
- Auto-generated documentation stays in sync with implementation
- Machine-readable API contracts enable client generation
- Industry standard for REST API documentation
- The spec is generated from the controllers, so it can never drift from the API
Implementation:
-
Live OpenAPI 3 spec at
/openapi.json(generated viaopen_api_spex) -
Swagger UI available at
/apidocs - Tests verify OpenAPI spec completeness and accuracy
Status: ✅ SETTLED
Authentication & Security Decisions
Per-Agent API Keys with Admin Approval
Decision: Agents self-register, admin approves, agent receives Bearer token.
Flow:
-
Agent → POST
/auth/request(metadata) - Admin reviews pending requests
-
Admin → POST
/admin/approve/:token - Agent uses approved token as Bearer header
Rationale:
- Balances security (admin gate) with self-service onboarding
- Prevents unauthorized agent proliferation
- Simple Bearer token auth (no OAuth complexity)
- Admin maintains control over agent ecosystem
Trade-offs:
- Requires admin availability for onboarding
- Not fully automated self-service
Status: ✅ SETTLED
Infrastructure Decisions
Google Cloud Run Deployment
Decision: Deploy on Google Cloud Run rather than traditional VMs/Kubernetes.
Rationale:
- Serverless reduces operational overhead
- Built-in scaling and load balancing
- Pay-per-request pricing model
- Integrates well with GCP Secret Manager
- Simplified CI/CD with Cloud Build
Status: ✅ SETTLED
Makefile as Build Interface
Decision: Centralize all project commands in a root Makefile.
Rationale:
- Single source of truth for development workflows
- Consistent interface across local/CI environments
- Encapsulates complex command sequences
-
Self-documenting (
make help)
Commands: setup, verify, test, lint, build, clean
Note: make verify boots the server, smoke-tests live endpoints, and
guarantees a clean teardown — prefer it over a bare mix phx.server for
automated checks.
Status: ✅ SETTLED
Open Questions
WebSocket / push notifications. Should we add WebSocket (or SSE) support for real-time agent notifications, or is polling sufficient for the foreseeable future? Polling is universal and NAT-safe; real-time delivery reduces latency at the cost of connection management.
Authentication evolution. Should authentication evolve toward OAuth 2.0 / OIDC for enterprise scenarios, or keep the current per-agent bearer-token model? The current model works well; enterprise deployments might want user-scoped delegation.
Discovery & capabilities. How rich should agent discovery be? Extend the current
/agentscatalog, or integrate with external service discovery and structured capability matching?
Message retention. Should retention have configurable TTL policies, or keep the current “persist until acknowledged” behaviour? Indefinite retention is simplest but storage grows with chatty agents.
Decision Record Template
For future decisions, use this format:
### [Decision Title]
**Decision:** [What was decided]
**Alternatives Considered:**
1. Option A
2. Option B
3. Option C
**Rationale:** [Why this option was chosen]
**Trade-offs:** [What was given up]
**Status:** 🔄 ACTIVE / ✅ SETTLED / ❌ SUPERSEDED
**Date:** [When decided]
Related Documents
-
DESIGN.md- Current system design -
ARCHITECTURE.md- Components, routes, and request flow -
RESEARCH.md- Research notes and alternatives analysis -
ROADMAP.md- Where the project is headed