Skip to content
AGNT

Backend

Database & models.

PostgreSQL 16 with the pgvector extension. SQLAlchemy 2.0 async ORM. 45 models live in agnt-backend/app/db/models.py— a single file so the whole schema is greppable in one place.

Engine configuration

The async engine is created in app/db/session.py. It runs with a large pool because scheduler jobs, webhook handlers, and the A2A public API all contend for connections.

pythonapp/db/session.py (abbreviated)
engine = create_async_engine(
    settings.DATABASE_URL,
    pool_size=100,
    max_overflow=50,
    pool_pre_ping=True,
    future=True,
)

async_session = async_sessionmaker(engine, expire_on_commit=False)

async def get_db() -> AsyncIterator[AsyncSession]:
    async with async_session() as session:
        yield session

Migrations

Alembic with sequential numbered migrations. Every migration file in agnt-backend/alembic/versions/ is named NNN_description.py. Upgrade paths are chained via down_revision. Run alembic upgrade head after every pull.

All models

Models are grouped by domain for navigation. Line numbers are pinned to the current app/db/models.py.

Identity & channels

ModelLinePurpose
User34Primary user row. Holds city, language, cp_agent_id, credits.
UserChannel94Messaging channel bindings: Telegram, WhatsApp, Instagram IDs.
UserMemory109Persistent user memory chunks. Backed by pgvector embeddings.
Session141JWT session anchor for revocation and audit.
Reminder125User reminders scheduled via set_reminder tool.
Interaction165Every inbound and outbound message, including A2A calls (source='external_agent').

Developer keys & webhooks

ModelLinePurpose
ApiKey189External agent API keys. Tier, bookings_total, last_used_at.
WebhookSubscription219Outbound webhook destinations per ApiKey.
WebhookDelivery243Individual delivery attempts with retry state.
ApiKeyUsageEvent268Metered billing ledger for booking.confirm and other paid intents.

Credits & referrals

ModelLinePurpose
CreditTransaction288Append-only credit ledger. Writes require SELECT FOR UPDATE.
Referral300User referral graph with expiry.

Venues

ModelLinePurpose
Venue311Core venue row. Slug, category, area, city, tags, priority_rank, referral_fee_pct.
VenueBooking349Booking rows. Party size, slot time, status, external_ref.
VenueClient372Links a business user to a venue they own or manage. Holds cp_agent_id.
BookingRating395Post-visit ratings with comments.
VenueKnowledgeSource411Uploaded venue knowledge (menu PDFs, URLs, manual text).
VenueClaim426Claim requests for venues listed publicly but not yet owned.
VenueChunk460pgvector chunks of venue knowledge for RAG retrieval.

Cities & lists

ModelLinePurpose
City470Supported cities: Canggu, Seminyak, Ubud, etc.
CityAmbassador487Local ambassadors promoting AGNT in a given city.
UserList444User-curated venue lists (wishlists, favourites).

Agents & A2A

ModelLinePurpose
A2AEnvelope525Local mirror of an outbound A2A envelope. Status transitions via ENVELOPE_TRANSITIONS.
AgentCard708Well-known AgentCard published by each agent on the network.
CardResponse729Per-user responses to generated shareable cards.

Commerce & accounting

ModelLinePurpose
CommerceLedger549Fee collection ledger. Pairs with Stripe events.
B2BOnboardingSession501Multi-step venue onboarding state machine.
AccountingDocument678Invoices, receipts, credit notes for business clients.
AccountingLedgerEntry692Double-entry accounting lines for each document.

Social graph

ModelLinePurpose
UserFollowsTaste566Taste-based follow relationships between users.
PushSubscription577Web Push subscription state.

Observability

ModelLinePurpose
AnalyticsEvent591Generic analytics sink for product events.
ConversationSnapshot601Point-in-time snapshots of a conversation for replay or audit.
AffiliateClick617Click-through events on affiliate links.
ErrorLog743Structured error log with context metadata.

Dupe search & diet

ModelLinePurpose
PriceWatcher628Standing price-watch jobs on Shopee/Tokopedia/Lazada products.
FoodDiary643Calorie scan history per user with macro breakdowns.

Transport

ModelLinePurpose
TransportBooking661Lalamove courier bookings with quote + confirmation state.

Fleet memory

ModelLinePurpose
ProjectMemory761Project-scoped memory entries for the agent fleet.

CRM

ModelLinePurpose
CrmContact787Venue-side contact records.
CrmDeal810Sales pipeline deals with value and stage.
CrmNote834Free-form notes attached to contacts or deals.
CrmActivity846Activity timeline entries (call, email, meeting).

Knowledge graph

ModelLinePurpose
EntityNode868Typed entity node for the AGNT knowledge graph.
EntityEdge884Directed edges between entity nodes with a relation type.

Conventions

  • UUIDs as primary keys, generated server-side via uuid_generate_v7() from the pgcrypto-compatible extension.
  • Timestamps are timestamptz with server_default=func.now().
  • Status columns have both an application-level state machine in a2a_enums.py and a DB CHECK constraint from migration 016 onwards. Application validation runs first; the DB check is belt-and-braces.
  • Money is stored as Numeric(10, 2) in the display table and as Integer cents in high-throughput ledgers.

Locking & concurrency

Two patterns matter when touching money or credits:

  1. credit_manager.py always uses SELECT ... FOR UPDATE on the user row before adjusting balance.
  2. commerce.py uses Stripe idempotency keys on every payment operation and, for critical money jobs, takes a Postgres advisory lock as a fallback to the Redis-based scheduler lock.

Related