Skip to content

Domain Models

Miranda uses UUID primary keys on all models via the HasUuid concern. All models belong to a Foundation scope, ensuring multi-tenant data isolation.

The root tenant model. Every other model in the system belongs to a foundation.

FieldTypeDescription
brand_colorsarrayCustom brand color palette
settingsarrayFoundation-wide configuration
vocabulary_overridesarrayCustom terminology (e.g., “donor” → “supporter”)
enabled_modulesarrayFeature flags for active modules
directory_listedbooleanWhether foundation appears in the public directory
safety_modebooleanRestricts destructive operations when enabled
trial_ends_atdatetimeTrial expiration (null = no trial)
frozen_atdatetimeAccount freeze timestamp (null = active)

Key relationships: users, donationPages, donations, scholarships, donorLinks, newsletterSubscriptions, roles, site

Methods:

  • isFrozen() — Returns true if the account is frozen
  • isTrialing() — Returns true/false/null (null = never trialed)

Public-facing website configuration for a foundation. One-to-one with Foundation.

FieldTypeDescription
custom_fontsarrayFont configuration for the public site

Relationships: foundation, pages, enabledPages (filtered + ordered by sort_order)

Individual pages within a foundation’s public site.

FieldTypeDescription
blocksarrayPage content as a block structure
enabledbooleanWhether the page is published

Relationships: site (FoundationSite)


The central person record. A contact can have multiple relationship types (donor, applicant, subscriber, general) with a single foundation.

FieldTypeDescription
first_namestringFirst name
last_namestringLast name
addressarrayStructured address data
communication_preferencesarrayOpt-in/out preferences per channel
first_contact_atdatetimeWhen this contact was first added

Key relationships: foundation, relationships, tags (many-to-many via contact_tag), activities, notes, donations

Computed attributes:

  • full_name — Concatenated first + last name
  • relationship_types — Array of active relationship type values (appended by default)

Methods:

  • hasRelationship(ContactRelationshipType $type) — Check if a relationship exists
  • addRelationship(ContactRelationshipType $type, ?array $metadata) — Create or find a relationship

Join record that assigns a relationship type to a contact within a foundation.

FieldTypeDescription
typeContactRelationshipTypeThe relationship type enum
metadataarrayAdditional context for this relationship
assigned_atdatetimeWhen the relationship was established

Freeform labels applied to contacts for organization and segmentation.

Relationships: foundation, contacts (many-to-many via contact_tag with foundation_id pivot)

Reusable filter criteria for querying contacts.

FieldTypeDescription
criteriaarrayFilter rules for building the segment query

Timeline events recorded against a contact.

FieldTypeDescription
typeActivityTypeThe activity type enum
metadataarrayEvent-specific data

Free-text notes attached to a contact by a user.

Relationships: contact, user, foundation


A single financial transaction.

FieldTypeDescription
amountintegerAmount in cents
platform_feeintegerPlatform fee in cents
donor_covered_feesbooleanWhether the donor opted to cover processing fees
typeDonationTypeone_time or recurring
statusDonationStatuspending, succeeded, failed, refunded
recurring_intervalRecurringIntervalmonthly, quarterly, annual (nullable)
metadataarrayStripe metadata and other details
donated_atdatetimeWhen the donation was made

Relationships: foundation, contact, donationPage

A configurable page for accepting donations. Supports multiple page types with type-specific configuration.

FieldTypeDescription
suggested_amountsarrayPreset donation amount options
allow_custom_amountbooleanWhether donors can enter a custom amount
allow_recurringbooleanWhether recurring donations are enabled
allow_donor_covers_feesbooleanWhether the fee-coverage option is shown
statusDonationPageStatusdraft, published, offline
typeDonationPageTypePage type (general, scholarship, campaign, memorial, emergency, sustainer)
type_configarrayType-specific configuration (see Enums reference)

Relationships: foundation, donations, scholarship (via type_config->scholarship_id)

A donor identity that can span multiple foundations. Tracks lifetime giving across the platform.

FieldTypeDescription
lifetime_givendecimalTotal giving across all foundations
first_gift_atdatetimeFirst donation timestamp
last_gift_atdatetimeMost recent donation timestamp

Relationships: foundationLinks, newsletterSubscriptions

Links a DonorProfile to a specific Foundation, with per-foundation giving stats.

FieldTypeDescription
newsletter_subscribedbooleanNewsletter opt-in for this foundation
total_givendecimalTotal given to this foundation
first_gift_atdatetimeFirst gift to this foundation
last_gift_atdatetimeMost recent gift to this foundation

Relationships: donorProfile, foundation, contact

Tracks newsletter subscription state per donor per foundation.

FieldTypeDescription
subscribedbooleanCurrent subscription status

A one-time broadcast message sent to a segment of contacts.

FieldTypeDescription
channelCampaignChannelemail or sms
statusCampaignStatusdraft, scheduled, sending, sent
segment_criteriaarrayContact filter criteria for targeting
statsarrayDelivery/open/click statistics
scheduled_atdatetimeWhen the campaign is scheduled to send
sent_atdatetimeWhen the campaign was actually sent

Relationships: foundation, communicationLogs

Individual message delivery record.

FieldTypeDescription
channelCampaignChannelemail or sms
directionCommunicationDirectionoutbound or inbound
statusCommunicationStatusDelivery status (sent, delivered, opened, clicked, bounced, failed)

Relationships: contact, campaign

Reusable message templates with merge field support.

FieldTypeDescription
channelCampaignChannelemail or sms
merge_fieldsarrayAvailable merge fields and their mappings

An automated multi-step communication flow triggered by a specific event.

FieldTypeDescription
triggerSequenceTriggerWhat event starts the sequence

Relationships: foundation, steps (ordered by position), enrollments

A single step within a sequence.

FieldTypeDescription
channelCampaignChannelemail or sms
positionintegerStep order within the sequence
delay_hoursintegerHours to wait after previous step

Tracks a contact’s progress through a sequence.

FieldTypeDescription
next_step_atdatetimeWhen the next step should execute
enrolled_atdatetimeWhen the contact entered the sequence
completed_atdatetimeWhen the contact finished (null = in progress)

Relationships: sequence, contact, currentStep


A scholarship program with configurable application form and award limits.

FieldTypeDescription
amountintegerAward amount in cents
max_awardsintegerMaximum number of awards
form_fieldsarrayCustom application form field definitions
deadlinedateApplication deadline
statusScholarshipStatusLifecycle status

Relationships: foundation, applications, disbursements

An individual application submitted for a scholarship.

FieldTypeDescription
responsesarrayApplicant’s form field responses
attachmentsarrayUploaded file references
stageApplicationStagenew, under_review, accepted, declined
sourceApplicationSourceform, api, webhook
submitted_atdatetimeSubmission timestamp

Relationships: foundation, scholarship, contact

A financial disbursement (scholarship award, grant, or operational expense).

FieldTypeDescription
amountintegerAmount in cents
categoryDisbursementCategoryscholarship, grant, operational, program, admin
disbursed_atdatetimeWhen the disbursement was made

Relationships: foundation, contact, scholarship


An authenticated user belonging to a foundation.

FieldTypeDescription
roleUserRolePlatform-level role (owner, admin, member, readonly)
email_verified_atdatetimeEmail verification timestamp

Relationships: foundation, teamRole (Role model for granular permissions)

Foundation-scoped role with custom permissions.

FieldTypeDescription
permissionsarrayGranular permission flags
is_defaultbooleanWhether this is the default role for new team members

Pending invitation to join a foundation’s team.

FieldTypeDescription
accepted_atdatetimeWhen the invite was accepted (null = pending)
expires_atdatetimeInvitation expiration

Methods:

  • isExpired() — Returns true if the invitation has expired
  • isAccepted() — Returns true if the invitation has been accepted