core PK: id 10 required 3 unique

Description

Represents a personalized referral invitation generated by a peer mentor to recruit new members. Stores the invite link token, QR code data, sharing metadata, and tracks the invite's lifecycle from creation through conversion.

18
Attributes
6
Indexes
7
Validation Rules
12
CRUD Operations

Data Structure

Name Type Description Constraints
id uuid Primary key
PKrequiredunique
inviter_user_id uuid FK to users — the peer mentor who generated this invite
required
organization_id uuid FK to organizations — the org context under which the invite was created
required
invite_token string Unique URL-safe token embedded in the invite link and QR code
requiredunique
invite_url string Full resolved invite URL (base URL + token path)
requiredunique
qr_code_data text Base64-encoded QR code image data or SVG string for display in app
-
status enum Lifecycle status of the invite
required
expires_at datetime UTC timestamp after which the invite link is no longer valid. Null means no expiry.
-
max_uses integer Maximum number of times this invite can be used. Null means unlimited.
-
use_count integer Number of times this invite link has been followed and resulted in a signup attempt
required
conversion_count integer Number of successful conversions (completed signups) attributed to this invite
required
share_channels json Array of channels through which this invite was shared (e.g. ['sms', 'email', 'qr', 'link_copy'])
-
custom_message text Optional personalized message the inviter attached when sharing
-
target_role enum The intended role for the invited user upon signup
-
created_at datetime UTC timestamp when the invite was created
required
updated_at datetime UTC timestamp of last status change or metadata update
required
revoked_at datetime UTC timestamp when the invite was manually revoked. Null if not revoked.
-
revoked_by_user_id uuid FK to users — who revoked the invite (inviter or org admin)
-

Database Indexes

idx_referral_invites_invite_token
btree unique

Columns: invite_token

idx_referral_invites_inviter_user_id
btree

Columns: inviter_user_id

idx_referral_invites_organization_id
btree

Columns: organization_id

idx_referral_invites_status
btree

Columns: status

idx_referral_invites_org_status
btree

Columns: organization_id, status

idx_referral_invites_inviter_created
btree

Columns: inviter_user_id, created_at

Validation Rules

invite_token_format error

Validation failed

invite_url_format error

Validation failed

expires_at_future error

Validation failed

custom_message_length error

Validation failed

valid_target_role error

Validation failed

revocation_requires_auth error

Validation failed

use_count_non_negative error

Validation failed

Business Rules

invite_token_uniqueness
on_create

Each invite token must be globally unique and cryptographically random (minimum 32 bytes of entropy). Tokens must never be reused, even after expiry or revocation.

Enforced by: ReferralLinkService
org_scoped_invite
on_create

An invite is always scoped to the inviter's current organization. A user cannot create an invite on behalf of an organization they do not belong to.

Enforced by: ReferralLinkService
active_invite_limit_per_user
on_create

A peer mentor may have at most one active invite link at a time per organization. Creating a new invite automatically revokes the previous active invite for that user in that org.

expired_invite_not_usable
always

Invite links with status 'expired' or 'revoked' must not allow new referral_tracking entries to be created. The backend validates expiry on every inbound link follow.

max_uses_enforcement
on_update

When max_uses is set and use_count reaches max_uses, the invite status is automatically set to 'converted' and further follows are rejected.

conversion_count_not_exceed_use_count
on_update

conversion_count must always be <= use_count. A conversion requires a prior tracked use.

Enforced by: ReferralLinkService
referral_program_module_gate
on_create

Referral invites can only be created when the referral-program module is enabled for the user's organization. The backend checks the organization's module toggle before allowing creation.

Storage Configuration

Storage Type
primary_table
Location
main_db
Partitioning
No Partitioning
Retention
Permanent Storage