Skip to main content

The Villa Life Platform Specification 2025-10-21

Executive Summary

This document defines the database architecture and backend platform for The Villa Life (TVL) — a next-generation hospitality and property management ecosystem. The platform is designed to support thousands of villas at launch, with a scalable foundation that can grow to millions of listings across multiple business models — including private villas, corporate retreats, and white-label marketplaces. At its core, TVL’s architecture unifies tenancy, supply, booking, pricing, and financial operations under a clean, modular data model that preserves data isolation, extensibility, and auditability at every level.

Design Philosophy

“Model for the future, implement for now.” The schema and service architecture implement the complete logical model from day one, even if the MVP only activates a subset of functionality. This allows the UI, APIs, and data integrations to be built against the future state, avoiding refactors as the platform scales.

  • Full schema readiness: All core entities (Org, Account, Space, Booking, RatePlan, Payment) exist from the start.
  • Incremental rollout: Early releases use simplified data paths but leverage the same underlying structure.
  • Longevity built-in: The platform can evolve from villa management to enterprise-grade distribution without structural change.

Core Design Principles

Tenant Isolation & Multi-Org Scalability

All data is partitioned by org_id, providing logical multitenancy.
Orgs represent top-level entities (owners, operators, marketplaces).
Accounts represent operational contexts or sub-tenants within an Org.

This structure supports owner-managed listings, TVL-managed properties, and partner-operated networks under a unified schema.
Why it matters: TVL can scale horizontally, host multiple partner brands, and support co-management — without cross-data leakage or schema refactoring.

Composable Data Domains

The platform is organized into modular, composable domains, each representing a major functional pillar of the system.

DomainDescriptionKey Entities
Tenancy & IdentityWho owns and acts on behalf of whomOrg, Account, User, Membership
Authorization & Access ControlRole- and scope-based permissions across data domainsRole, Permission, PolicyRule
Supply (Spaces & Units)Inventory of villas, rooms, and assetsSpace, Unit, AccountSpaceRole
Availability, Calendars & BlockingTime-based inventory managementAvailabilityCalendar, Block, Hold
Pricing, Fees & Revenue RulesConfigurable pricing and commission modelsRatePlan, FeeRule, RevenueRule
Quotes, Holds & BookingsTransaction lifecycle from inquiry to confirmed stayQuote, Hold, Booking
Payments, Payouts & FinancialsFinancial transactions, reconciliation, and reportingPayment, Payout, Transaction, Ledger
Content, Media & MetadataDescriptive, visual, and structured listing dataDescription, MediaAsset, Attribute, Tag
Channels, Distribution & SyndicationData exchange with OTAs, partners, and white-label sitesChannel, ChannelFeed, ChannelListing
Delegation & Multi-Org CollaborationShared management and cross-tenant collaborationDelegation, ResourceReference
Search, Discovery & IndexingOptimized data structures for fast search and filteringSearchIndex, DiscoveryIndex
Analytics, Events & Audit TrailsObservability, metrics, and compliance-grade audit logsEvent, AuditEvent, MetricSeries
System Architecture & Data InfrastructurePhysical architecture and data pipeline strategyDatabase, Cache, Queue, Warehouse
Scalability, Resilience & Lifecycle ManagementGrowth, reliability, and continuous evolutionShard, WorkerPool, Backup, FeatureFlag

Why it matters: Each domain is independently maintainable and extensible.
New capabilities (e.g., corporate retreats, branded marketplaces, AI-driven pricing) can be layered in without schema rewrites.


Event-Driven Consistency

Rather than relying solely on synchronous updates, all domains publish Events for downstream processing — powering search reindexing, analytics aggregation, and feed synchronization.
This approach ensures eventual consistency across all services and enables robust asynchronous scaling as the platform grows.

Transparency, Auditability & Compliance

Every key operation — bookings, payouts, delegation changes — is logged as a verifiable AuditEvent with user, timestamp, and state diff.
The schema is built to meet SOC2, PCI-DSS, and GDPR requirements out of the box.

Future-Proof Extensibility

  • Every major entity is linked to org_id and account_id, allowing federated data ownership.
  • Financial logic is modular — supporting complex revenue splits, taxes, and commissions.
  • Availability and pricing are flexible — supporting real-time sync, dynamic pricing, and channel-specific rules.
  • The system anticipates distributed tenancy, white-label syndication, and AI-powered automation.

Tenancy & Identity

Overview

Tenancy & Identity define who owns what and who can act on behalf of whom across the platform.
It is the foundational layer that governs multi-tenancy, account delegation, and user identity.
This structure separates the tenant boundary (Org) from the actors (Accounts) that operate within it, ensuring clean isolation, flexible delegation, and scalable access control.

TL;DR

  • Org = Tenant boundary (brand, company, or marketplace).
  • Account = Actor within an Org (owner, manager, marketplace, or internal ops).
  • User = Person identity (email-based, global).
  • Membership = Binding of User → Org[/Account] + Role.
  • Role = Permission set describing what actions the User can take.
  • Accounts are mandatory per Org, with one default Account auto-created (is_default=true).

This structure supports villa-only use today and scales to 1M+ listings and cross-org collaborations without refactors.


Relationships & Cardinality

  • Org → Account: 1→* — each Org has at least one Account; one is_default=true.
  • Org → Membership: 1→* — every Membership belongs to an Org.
  • Account → Membership: 1→* — Membership may also be Org-wide (account_id = NULL).
  • User → Membership: 1→* — a User may belong to many Orgs/Accounts.
  • Membership → Role: 1→1 — each Membership carries exactly one Role.
  • Org → Role: 1→* — Roles are seeded per Org or globally shared.
  • All actor-owned data → (Org, Account): required foreign keys for ownership and isolation.

Core Concepts

Org (Tenant)

Purpose: Represents the top-level business boundary and isolation scope.
Owns: Accounts, Memberships, and all tenant data (Spaces, Bookings, Pricing, etc.).
Lifecycle: Created during onboarding; deactivated or suspended but never deleted for audit reasons.
Isolation: Always filters queries by org_id.

Account (Sub-tenant / Actor within an Org)

Purpose: Represents the entity that owns, manages, or operates assets within an Org (e.g., property owner, manager, marketplace, internal ops).
Always present: One default Account created automatically on Org creation.
Attributes: type = owner|manager|marketplace|internal, is_default = true|false.
Constraints: (org_id, is_default) unique to enforce single default per Org.

User (Person)

Purpose: Global individual identity.
Uniqueness: Unique by email; persistent even across multiple Orgs.
Lifecycle: Never hard-deleted; deactivation via deleted_at.
Why: Allows users to act across multiple Orgs (multi-tenant participation).

Membership (User to Org[/Account] + Role)

Purpose: Defines where and how a User can act.
Scope:

  • account_id = NULL → Org-wide access.
  • account_id = value → Account-specific access. Lifecycle: Can end (ended_at) but retained for audit; no hard deletes.

Role (Permission bundle)

Purpose: Named profile that defines which permissions a Membership grants (e.g., admin, owner_admin, ops, viewer).
Why: Enables consistent permission assignment and auditability.
Lifecycle: Static seeds, but can be extended per Org if needed.

Authorization & Access Control

Overview

Authorization & Access Control define what actions users can take and where they can take them within the system.
It combines Membership-based scoping (Org and Account) with Role-based permissions (RBAC) to form a clear, auditable, and extensible model.
This layer ensures that every API call, UI action, and data mutation respects the correct Org and Account boundaries.

TL;DR

Access = scope + permissions: scope from Membership, actions from Role→Permission.
Org-wide Memberships (account_id = NULL) grant access to all Accounts within that Org.
Account Memberships restrict access to the given Account’s assets.
RBAC now; ABAC later (via policy_rules).
All actor-owned resources include (org_id, account_id); queries always filter within this scope.
MVP: explicit, auditable RBAC suitable for villa-only operations; scalable to multi-brand marketplaces.


Relationships & Cardinality

  • Org → Account 1:* — tenancy boundary; all authorization happens within an Org.
  • Org → Membership 1:* — defines who can act within the Org.
  • Account → Membership 1:* — Memberships may target a specific Account.
  • Membership → Role 1:1 — each Membership carries one Role.
  • Role → Permission 1:* — Roles bundle Permissions.
  • Org → PolicyRule 1:* — optional future ABAC policies (disabled at MVP).
  • Actor-owned data → (Org, Account) — required FKs for authorization scope.

Core Concepts

Membership (scope of authority)

Connects a User to an Org (and optionally an Account) granting privileges of a Role.
Org-wide = account_id NULL; Account-level = populated.
Ends via ended_at; retained for audit trail.

Role (permission bundle)

Named grouping of permissions (admin, owner_admin, manager, ops, viewer).
Globally seeded defaults, extendable per Org.

Permission (action registry)

Atomic verbs recognized by the system (e.g., space.read, booking.manage, pricing.edit).
Versioned and centrally maintained.

Associates Roles with Permissions; each mapping has an effect (allow|deny).
Deny wins over allow.

PolicyRule (future ABAC)

Conditional allow/deny rules with JSON conditions (e.g., channel, region).
Disabled for MVP.


Rationale

Separation of scope vs authority: Membership determines where, Role determines what.
Predictable enforcement: queries filter by (org_id, account_id).
Scales from single villa to multi-Org marketplaces.
Future-proof: ABAC and Row-Level Security layer on without schema changes.


MVP Implementation (villa-only)

Seed Roles: admin, ops, owner_admin, manager, viewer.
Seed Permissions (core verbs for account, space, pricing, booking actions).
Role bundles:

  • admin: all permissions
  • ops: all except account.set_default
  • owner_admin: manage own Spaces, Bookings, Pricing
  • manager: operate Bookings within Account
  • viewer: read-only

Org creator gets Org-wide admin Membership; default Account auto-created.


Operational Notes

  • Cache effective (scope + permissions) set; invalidate on Membership/Role change.
  • Index memberships (org_id,user_id,account_id) and role_permissions (role_id,permission_id).
  • Log all access-denied events and Role changes.
  • org_id filter mandatory to prevent cross-tenant leakage.

Availability, Calendars & Blocking

Overview

Availability manages time-based inventory (Bookings, Holds, Blocks, iCal feeds).
Ensures safe coordination across channels and prevents double-bookings.

TL;DR

Single authoritative calendar per Space (villa MVP; Unit-level later).
Bookings, Holds, Blocks share same surface → precedence Booking > Hold > Block.
iCal export/import with tokenized URLs.
InventoryLock prevents double-sells.


Relationships & Cardinality

  • Org → Space 1:*
  • Space → AvailabilityCalendar 1:1
  • AvailabilityCalendar → Booking 1:*
  • AvailabilityCalendar → Hold 1:*
  • AvailabilityCalendar → Block 1:*
  • Space → iCalFeed 1:*
  • Actor-owned data → (Org, Account)

Core Concepts

AvailabilityCalendar

Authoritative record of a Space’s inventory. Keys: (org_id, space_id).

Booking

Confirmed reservation; blocks time and overrides all other entries.
Lifecycle: pending → confirmed → checked_in → completed|canceled.

Hold

Temporary lock (TTL 10–30 min) during checkout; converted or expires.

Block

Non-booking busy period (maintenance, owner stay, external iCal).
source = manual|owner|partner|external|ops|system.

InventoryLock

DB or advisory lock guarding (calendar_id,start,end) per transaction.

iCalFeed

Handles outbound/inbound calendar sync. Tokenized URL; tracks etag & last_modified.


Rationale

Unified time model simplifies conflict resolution.
Bookings always override other events.
iCal imports idempotent and secure.
Audit trail for every change.


MVP Implementation

  • One calendar per Space.
  • Acquire InventoryLock → create Hold → confirm → release.
  • Two outbound iCal feeds (public, owner).
  • External iCal imports as Blocks using If-None-Match headers.
  • UI shows merged timeline (Bookings + Blocks).

Operational Notes

  • Store UTC half-open intervals [start_at,end_at).
  • EXCLUDE USING gist(calendar_id WITH =, time_range WITH &&) to prevent overlap.
  • Materialized daily availability views for search.
  • Bookings > Holds > Blocks > Available.
  • Imported blocks never override confirmed Bookings.

Pricing, Fees & Revenue Rules

Overview

Defines rate computation and revenue allocation. Separates pricing logic from application (Quotes, Bookings).

TL;DR

Pricing = Rules + Context.
RatePlans define base rates; FeeRules add costs; RevenueRules split income.
Quotes snapshot pricing state at booking time.
Villa MVP: nightly rate + cleaning fee + fixed commission split.


Relationships & Cardinality

  • Org → Space 1:*
  • Space → RatePlan 1:*
  • RatePlan → RateRule 1:*
  • RatePlan → FeeRule 1:*
  • RatePlan → RevenueRule 1:*
  • RatePlan → Quote 1:*
  • Quote → Booking 1:1

Core Concepts

RatePlan

Defines pricing set for a Space. (org_id,account_id,space_id).

RateRule

Base price and modifiers (season, LOS, lead time, channel).
Priority: date > stay length > lead time > channel.

FeeRule

Extra charges (fixed or percent) basis per stay|night|guest.

RevenueRule

Splits gross between Accounts and TVL. e.g. Owner 80%, TVL 20%.

Quote

Snapshot of evaluated pricing; immutable after conversion to Booking.


Rationale

Separation of definition vs application.
Explicit financial rules aid audit and transparency.
Scales to taxes, promos, and multi-party payouts.


MVP Implementation

  • One RatePlan per Space (“Standard Rate”).
  • Flat nightly rate (+seasonal multiplier).
  • Cleaning fee + 20% TVL commission.
  • Quotes generated at checkout; frozen on confirmation.

Future Enhancements

Dynamic pricing API integration.
Multi-currency support.
Tax engine and rule chaining.
Accounting sync for ledger integration.


Operational Notes

  • Compute pipeline: RatePlan + Rules → Quote → Booking.
  • Store minor units (cents).
  • Index (org_id,space_id,valid_from) for RatePlans.
  • Audit rate changes.
  • Cache daily rates per Space for search.

Quotes, Holds & Bookings

Overview

Manages the complete reservation lifecycle — from inquiry to final booking — tying together Pricing, Availability, and Payments.

TL;DR

Quote → Hold → Booking is the core flow.
Quotes contain pricing snapshots.
Holds reserve inventory temporarily.
Bookings finalize stays and drive payments and reporting.
Villa MVP = single Unit bookings; simple state machine.
Future-ready = multi-Unit, multi-Account, and channel-aware lifecycle.


Relationships & Cardinality

  • Org → Space 1:*
  • Space → Quote 1:*
  • Quote → Hold 1:1
  • Quote → Booking 1:1
  • AvailabilityCalendar → Hold 1:*
  • AvailabilityCalendar → Booking 1:*
  • Booking → Payment/Invoice 1:*
  • Actor-owned data → (Org, Account)

Core Concepts

Quote

Priced offer based on RatePlan, dates, and occupancy.
Immutable snapshot (fields: checkin/checkout, nights, guests, totals).

Hold

Temporary inventory lock (TTL 15–30 min) during checkout.
Expires automatically or converts to Booking.

Booking

Authoritative reservation record.
State machine: pending → confirmed → checked_in → completed | canceled.
Immutable except for state transitions.
Links to Quote and Payments.


Rationale

Predictable workflow; atomic state changes for auditability.
Optimistic concurrency prevents double-booking.
Unified record for operations and finance.


MVP Implementation

  1. Quote generated from RatePlan; expires after 30 min.
  2. Hold created when checkout starts; TTL 15 min.
  3. Booking confirmed after payment; Hold released.
  4. Triggers calendar update and iCal feed regeneration.
  5. Illegal state transitions rejected with audit log.

Operational Notes

  • Use InventoryLock on create.
  • Index bookings on (org_id, space_id, checkin).
  • Never delete bookings; mark canceled_at.
  • Emit events: quote.created, booking.confirmed, booking.canceled.

Payments, Payouts & Financials

Overview

Tracks all money movement — from guest payments to owner payouts — with immutable journal entries and auditable ledgers.

TL;DR

Payments = inflows (guest → platform).
Payouts = outflows (platform → accounts).
Transactions = immutable journal entries.
Villa MVP: record payments & manual payouts.
Future-ready: automated settlements, multi-currency, and compliance.


Relationships & Cardinality

  • Booking → Payment 1:*
  • Booking → Payout 1:*
  • Payment → Transaction 1:*
  • Payout → Transaction 1:*
  • Org → Ledger 1:1
  • Ledger → Transaction 1:*
  • Payment → Refund 1:*

Core Concepts

Payment

Guest inflow linked to Booking.
amount, currency, status (pending|succeeded|failed|refunded).

Payout

Outgoing disbursement to owner/partner Account.
Created automatically when Booking completed.

Transaction

Atomic ledger entry (debit|credit) with category and timestamp.
Double-entry compliant.

Ledger

One per Org; aggregates Transactions and balance.

Refund

Negative Payment creating compensating Transactions.

BalanceSummary

Computed view of pending balances per Account.


Rationale

Immutable journal for compliance.
Lineage to Booking and RatePlan for traceability.
Separation of intent (Rules) vs actual (Transactions).
Scalable multi-Org financial framework.


MVP Implementation

  • Record Payments manually or via provider (Stripe).
  • Compute payouts from RevenueRules (Owner 80%, TVL 20%).
  • Insert Transactions for each Payment and Payout.
  • Refunds = negative Transactions.
  • Summaries by Org/Account for reporting.

Operational Notes

  • Amounts in minor units (cents).
  • Indexes on (org_id, booking_id, occurred_at).
  • Payments idempotent via reference token.
  • No soft deletes — use compensating entries.
  • Audit every status change.

Content, Media & Metadata

Overview

Defines how Spaces and Units are described, visualized, and enriched.
Separates marketing content from operational data for re-use and syndication.

TL;DR

Content = text and descriptions.
Media = photos/videos/docs.
Metadata = structured attributes + tags.
Villa MVP: descriptions, photo gallery, amenities.
Future-ready: multi-language localization and AI metadata.


Relationships & Cardinality

  • Org → Space 1:*
  • Space → MediaAsset 1:*
  • Space → Description 1:*
  • Space → Amenity 1:*
  • Space → Attribute 1:1
  • Space → Tag :
  • MediaAsset → Tag :

Core Concepts

Description

Marketing text (title, headline, body).
language_code, format (html|markdown).
Revisions versioned; archived for rollback.

MediaAsset

Images/videos/documents with ordering.
Fields: url, position, is_primary, caption, alt_text.
Stored in S3/CDN; metadata in DB.

Amenity

Boolean or parametric features (pool, wifi, parking).
Catalog-driven; used for search filters.

Attribute

Structured JSON metadata (e.g., {"max_guests":8,"bedrooms":4}).
Supports flexible feature expansion.

Tag

Categorical labels (theme, feature, marketing).
Multi-purpose for search and feeds.


Rationale

Decoupled presentation from data logic.
Reusable across web, marketing, and feeds.
Supports localization and versioning.
Structured metadata enables rich search and AI tagging.


MVP Implementation

  • One Description per Space (default language).
  • Photo gallery (5–20 images, ordered).
  • is_primary = true for cover photo.
  • Amenity catalog (~50 keys).
  • Attributes: max_guests, bedrooms, bathrooms, view.
  • Tags optional (e.g., “Seaside”, “Private Chef”).
  • Version changes logged to AuditEvents.

Operational Notes

  • URLs signed and CDN-served.
  • Index media_assets(space_id,position); GIN on attributes.
  • UTF-8 for localization.
  • Access limited to authorized Memberships.
  • Soft delete via deleted_at.
  • Pre-render cached HTML blobs for faster load.

Channels, Distribution & Syndication

Overview

Channels & Distribution govern how listings, rates, and availability are exported to and synchronized with external marketplaces and white-label sites.

TL;DR

  • Channel = logical external connection (Airbnb, VRBO, TVL Brand).
  • ChannelFeed = defines what data gets published (content, rates, availability).
  • ChannelListing = maps internal Space/Unit → external listing ID.
  • ChannelSync = records each import/export for observability. Villa MVP: iCal-based exports and manual listing links.
    Future: two-way API sync, channel rulesets, and white-label marketplaces.

Relationships & Cardinality

  • Org → Channel 1:*
  • Channel → ChannelFeed 1:*
  • Channel → ChannelListing 1:*
  • Space → ChannelListing 1:*
  • ChannelListing → ChannelSync 1:*
  • Space → ChannelBlock 1:* (imported busy dates)
  • Actor-owned data → (Org, Account)

Core Concepts

Channel

Represents an external integration.
type = ota | marketplace | api_partner | internal_brand
Active via API key or feed URL.

ChannelFeed

Specifies scope and format of data export (ical|json|xml|api). Supports per-audience feeds (public, owner, partner).

ChannelListing

Maps Space/Unit to external listing ID.
Tracks sync status and last updated time.

ChannelSync

Operational log of export/import events for debug and analytics.
Fields: direction, scope, started_at, status, message_log.

ChannelBlock

Imported busy dates from external feeds → internal Availability Blocks.


Rationale

Unified model for all distribution paths (OTA, partner, marketplace).
Traceable sync via ChannelSync.
Simple MVP (iCal) with extensibility for full API integration.
Tenant-safe: each Org manages its own channels and feeds.


MVP Implementation

  • Supported channels: Airbnb, VRBO, TVL public site.
  • Exports: Availability via iCal.
  • Imports: External iCal → ChannelBlock.
  • Manual external IDs per listing.
  • Sync logs retained 30 days.
  • Tokenized URLs; duplicate UIDs deduped.

Operational Notes

  • Jobs schedule syncs hourly (iCal) or real-time (API).
  • Index channel_listings(space_id,channel_id) unique.
  • Cache feeds with ETag headers.
  • Audit each sync with user and timestamp.

Delegation & Multi-Org Collaboration

Overview

Delegation enables cross-Org collaboration without breaking tenant isolation — for example, letting TVL Ops manage owner villas on behalf of clients.

TL;DR

Delegation = controlled permission grant from one Org/Account to another.
Ownership never changes; access is extended.
MVP: TVL Ops acts for owners.
Future: multi-brand partnerships, white-label marketplaces, API delegations.


Relationships & Cardinality

  • Org → Delegation 1:*
  • Account → Delegation 1:*
  • Delegation → ResourceReference 1:*
  • Org ↔ Org many-to-many via Delegation
  • Org → Membership 1:* (for DelegatedMembership resolution)

Core Concepts

Delegation

Record linking grantor Org → grantee Org.
scope = read|write|manage, resource_type = space|booking|pricing.
Active between start_at and end_at.

ResourceReference

Specific IDs shared under a Delegation (e.g., selected Spaces).

DelegatedMembership

Derived temporary Membership granting a user cross-Org access.

CollaborationLog

Audit trail of delegated actions (user, action, resource, timestamp).


Rationale

Enables co-management without data merging.
Audit trail + revocability for trust and compliance.
Foundation for B2B integrations and partner programs.


MVP Implementation

  • Owner Org delegates to TVL Ops Org (scope=manage, resource_type=space).
  • TVL Ops users gain derived manager role for those Spaces.
  • Revocation on contract end; logged in CollaborationLog.

Operational Notes

  • Authorization middleware checks Membership + DelegatedMembership.
  • Index delegations(grantor_org_id,grantee_org_id,resource_type,status).
  • Cascading revocation of derived Memberships.
  • Delegations signed and audited.

Search, Discovery & Indexing

Overview

Provides fast, filterable search for Spaces and Units by flattening operational data into search-optimized indexes.

TL;DR

SearchIndex = flat searchable fields.
DiscoveryIndex = availability-aware metadata.
Villa MVP: filter by location, price, bedrooms, amenities.
Future: full-text search, personalization, geo-distributed shards.


Relationships & Cardinality

  • Org → Space 1:*
  • Space → SearchIndex 1:1
  • Space → DiscoveryIndex 1:1
  • Space → Tag :
  • AvailabilityCalendar → DiscoveryIndex 1:*

Core Concepts

SearchIndex

Flattened record of Space fields (name, location, tags, price range, capacity).
Updated on change events.

DiscoveryIndex

Aggregated snapshot including availability and pricing facets.

FilterSet

Reusable JSON filter definitions for API queries.

SearchJob / ReindexTask

Async job keeping indexes up-to-date from domain events.


Rationale

Performance via denormalization.
Consistency from event-driven updates.
Tenant isolation by org_id.
Scalable for tens of thousands of listings.


MVP Implementation

  • Index active Spaces (status=active).
  • Fields: name, location, price_min/max, bedrooms, tags, amenities.
  • Availability flags (next 90 days).
  • Reindex triggered by Space, Price, or Booking event.
  • Filters: location, price_range, bedrooms, amenities, tags.
  • Sorted by price or capacity.

Operational Notes

  • Event-driven or batch reindex jobs.
  • Use PostgreSQL FTS or Elasticsearch.
  • Include (org_id,account_id) in index records.
  • Cache popular filters in Redis.
  • Monitor indexing latency and search performance.

Analytics, Events & Audit Trails

Overview

Captures every operational, behavioral, and financial change across the system — providing observability, compliance, and analytical insight.

TL;DR

  • Event = atomic record of something that happened.
  • AuditEvent = signed log of sensitive changes (who, what, when).
  • MetricSeries = aggregated time-series metrics.
    Villa MVP → capture CRUD events for Bookings, Spaces, and Payments.
    Future-ready → streaming analytics, ML pipelines, external BI feeds.

Relationships & Cardinality

  • Org → Event 1:*
  • Org → AuditEvent 1:*
  • User → Event 1:*
  • Resource → Event 1:*
  • Org → MetricSeries 1:*
  • Actor-owned data → (Org, Account)

Core Concepts

Event

Generic record of a system or user action.
Fields: org_id, account_id, user_id, resource_type, resource_id, event_type, payload, source, occurred_at, trace_id.
Append-only; never edited.

AuditEvent

Cryptographically verifiable record of sensitive state changes.
Includes before/after snapshots and signature.
Immutable; deletions logged as compensating events.

MetricSeries

Aggregated numeric data (bookings/day, revenue, latency).
Stored by time bucket and dimension (region, channel, account).
Feeds dashboards and BI tools.

EventStream / EventBus

Pub/Sub pipeline for internal and external consumers.
Guarantees at-least-once delivery.
MVP → in-process queue; Future → Kafka / PubSub.


Rationale

End-to-end traceability of system behavior.
AuditEvents for SOC2 / GDPR compliance.
Metrics enable real-time monitoring and decision-making.
Unified pipeline for DevOps and business intelligence.


MVP Implementation

  • Record booking.created|confirmed|canceled, space.updated, payment.succeeded.
  • Append to events table; nightly aggregate into metric_series.
  • Audit on updates / deletes to key tables with before|after JSON.
  • Sign AuditEvents with HMAC.
  • Simple dashboards for bookings, occupancy, revenue.

Operational Notes

  • Partition events by occurred_at.
  • Index (org_id, resource_type, resource_id, occurred_at).
  • Store AuditEvents in WORM media.
  • Retention 12–24 months; Metrics daily roll-ups.
  • Encrypt at rest; rotate keys.
  • Retry failed writes via dead-letter queue.
  • Monitor ingestion lag and consumer latency.

System Architecture & Data Infrastructure

Overview

Defines how all domains interconnect — databases, services, queues, caches, and analytics layers — to deliver a scalable and resilient backend.

TL;DR

  • Modular, service-oriented architecture around PostgreSQL.
  • Multi-tenant schema (org_id partitioning).
  • Redis for cache & queues.
  • Central Event Bus for async flows.
  • Villa MVP → single cluster, background jobs for sync & iCal.
  • Future → sharding, microservices, warehouse sync, data lake archives.

Relationships & Cardinality

  • DB Cluster → Org 1:* (soft multitenancy).
  • Org → Account / Space / Booking … 1:*
  • EventBus → Domain Services 1:*
  • Service → Cache 1:*
  • Service → DB Pool 1:*
  • Analytics Warehouse → Org many-to-many (partitioned per tenant).

Core Concepts

Relational Database (PostgreSQL)

Authoritative store for all structured data.

  • Single cluster per environment (core, analytics, jobs).
  • Each table includes org_id.
  • Uses foreign keys, partial indexes, and GIST ranges (for availability).
  • ACID guarantees for bookings & finance; JSONB flexibility for metadata.

Caching Layer

Redis for sessions, computed prices, availability fragments.
CDN (e.g., CloudFront) for media and feeds.
TTL-based invalidation on update events.

Message Queue / Event Bus

Decouples domain logic.
Jobs: imports, reindexing, feeds.
Events: booking.created, payment.succeeded.
Guarantee: at-least-once delivery with dedup by event_id.

Service Layer

Encapsulated APIs per domain:
identity-service, booking-service, pricing-service, finance-service, content-service, channel-service, delegation-service, analytics-service.
Communicate via REST / gRPC with shared auth middleware.

Data Warehouse / Analytics Layer

Event stream → staging → BigQuery/Snowflake.
Used for BI dashboards & forecasting.
MVP = batch ETL; Future = streaming sync.

File Storage & CDN

S3 for objects, CloudFront for distribution.
Signed URLs; lifecycle policies for archival.


Rationale

ACID integrity + logical isolation for tenants.
Stateless services for scalability.
Event-driven foundation for automation and analytics.
Security via encryption, network segmentation, and least-privilege IAM.


MVP Implementation (villa-only)

  • Single region (Postgres + Redis + CDN).
  • Core services containerized on Kubernetes.
  • Enabled domains: Identity, Auth, Supply, Availability, Pricing, Bookings, Payments, Content.
  • Async jobs for reindexing and iCal imports.
  • Search = Postgres FTS or small Elasticsearch node.
  • Observability = OpenTelemetry + ELK stack.
  • Security = TLS everywhere, JWT for auth, row-level isolation by org_id.

Future Enhancements

  • Horizontal sharding and multi-region replicas.
  • Streaming ETL to warehouse / data lake.
  • Microservice autoscaling via CI/CD.
  • IaC (Terraform) per service.
  • API Gateway for rate limiting & metrics.
  • Automated compliance checks and daily audits.

Operational Notes

  • Versioned migrations (Alembic / Liquibase).
  • Enforce FKs, unique constraints, and soft deletes.
  • Monitor replication lag and slow queries.
  • PITR backups (30-day retention).
  • Warm standby region for DR.
  • Secret rotation every 90 days.
  • Read replicas for analytics.
  • Isolated dev/staging/prod environments.

Scalability, Resilience & Lifecycle Management

Overview

Defines how the TVL system scales, adapts, and maintains reliability as data volume and concurrency increase.
Includes scaling patterns, operational resilience, schema lifecycle, and observability practices.

TL;DR

  • Scaling: horizontal service scaling + tenant partitioning by org_id.
  • Resilience: redundancy, retry queues, and stateless recovery.
  • Lifecycle: versioned migrations, feature flags, and schema evolution.
    Villa MVP: single-region, single-cluster core with nightly backups.
    Future-ready: multi-region sharding, rolling upgrades, autoscaling, continuous deployment.

Relationships & Cardinality

  • Org → DB Shard →1 (future) — each Org assigned to one shard.
  • Service → WorkerPool 1:* — services scale horizontally via replicas.
  • JobQueue → Worker 1:* — tasks distributed for concurrency.
  • EventBus → Consumer 1:* — each event may have multiple processors.
  • Actor-owned data → (Org, Account) ensures tenant isolation.

Core Concepts

Horizontal Scaling

Add service instances to handle higher load.
Stateless containers; sessions persisted via Redis.
Example: booking-service scaled to 20 replicas during high season.
MVP → manual; Future → auto-scaling by CPU/RPS metrics.

Database Partitioning

Distribute tenants across clusters or shards.
Partition by org_id, optionally by region (EU/US/APAC).
MVP → one cluster; Future → Shard Router Service.

Caching & Computed Stores

Relieve read load and speed response.
Redis for ephemeral data; materialized views for analytics; CDN for feeds.
TTL-based or event-driven invalidation.

Job Queues & Background Processing

Retryable, non-blocking workloads (imports, syncs, reindexes).
Redis or RabbitMQ as queue backend.
Jobs idempotent; guarantee at-least-once delivery.

Resilience & Fault Recovery

Patterns:

  • Circuit breakers on external calls.
  • Graceful degradation of non-critical features.
  • Dead-letter queues for failed jobs.
  • Heartbeat & health endpoints for liveness probes. MVP: basic retries; Future: distributed tracing & SLA metrics.

Schema & Version Management

Safe, backward-compatible evolution.

  • Versioned migrations (Alembic/Liquibase).
  • Feature flags for dependent changes.
  • Shadow writes for dual-schema rollouts.
    Policy: never destructive in active deployments.

Observability & Monitoring

Metrics: system health, queue depth, latency.
Traces: OpenTelemetry correlation from API → DB.
Logs: structured and searchable.
Tools: Grafana, Prometheus, ELK, or CloudWatch.
Alerts: SLA violations, replication lag, job failures.
MVP: central log aggregation + Slack/Email alerts.

Backups & Disaster Recovery

  • Point-in-time recovery via WAL logs.
  • Daily full backup to encrypted storage (30-day retention).
  • Standby replica auto-promoted on failure.
  • Quarterly DR simulations for validation.

Lifecycle Management

Ensures smooth evolution of system & schema.

  • Blue/green or rolling deploys.
  • Feature flag toggles for gradual rollout.
  • Parity across dev/staging/prod. MVP: manual deploys with migration hooks;
    Future: CI/CD with canary deploys and auto rollback.

Rationale

  • Elastic performance: horizontal scaling without redesign.
  • Predictable resilience: each layer (DB/cache/queue/service) recovers independently.
  • Operational safety: built-in backup, audit, and monitoring pipelines.
  • Continuous evolution: migration discipline + feature flag governance.
  • Future-proof: designed for multi-region scale and zero-downtime evolution.

MVP Implementation

  1. Database: single RDS instance; daily backups + replicas.
  2. Services: Kubernetes pods; manual HPA target.
  3. Queues: Redis job runner for iCal imports & search reindexing.
  4. Monitoring: uptime and slow-query logs.
  5. Resilience: idempotent retries for failed bookings/payments.
  6. Lifecycle: versioned migrations with manual approval.
  7. DR: warm standby region, <1-hour recovery objective.

Future Enhancements

  • Multi-shard router for org-based DB routing.
  • Autoscaling workers (dynamic by queue depth).
  • Global failover via DNS routing.
  • Zero-downtime migrations with background schema copy.
  • Automated rollback + feature flag reverts.
  • Network chaos testing for consistency validation.
  • Resilience automation via chaos engineering drills.
  • Unified dashboards (uptime, latency, throughput).
  • Predictive autoscaling before peak seasons.
  • Scheduled data-retention validation.

Operational Notes

Metrics to track:

  • DB latency, job throughput, cache hit ratio, API error rate.

Alerts:

  • Critical: DB unavailability, queue overflow, payout failures.
  • Warning: replication lag, stale index, cache degradation.

Release cadence:

  • Weekly features; monthly schema sync.

Change management:

  • All releases, migrations, and recoveries recorded as AuditEvents.

Security posture:

  • Secrets rotated quarterly; static scans pre-deploy.

Uptime targets:

  • MVP = 99.5%, Future = 99.9% global.

Cost optimization:

  • Non-peak autoscaling down; cold storage for expired data.