Database Schema
Overview
This document describes the database schema and data persistence layer for the Absence Management module. The system uses MongoDB as the primary database with Mongoose as the ODM layer.
Database Schema
Absence Collection
Collection Name: absence
The absence collection stores all absence records with the following schema structure:
{
_id: ObjectId, // Primary key
note: String, // Optional description
start: String, // Start date/time (ISO string) - REQUIRED
end: String, // End date/time (ISO string) - REQUIRED
entireBusiness: Boolean, // Affects entire business flag
members: [ObjectId], // References to Member collection
memberIds: [String], // Array of member ID strings
locations: [LocationSchema], // Embedded location documents
type: String, // Absence type (vacation, holiday, break) - REQUIRED
timeZone: String, // Timezone identifier - REQUIRED
meta: MetaSchema, // Metadata information
stateHistory: [StateHistorySchema], // State tracking for soft deletes
createdAt: Date, // Auto-generated creation timestamp
updatedAt: Date // Auto-generated update timestamp
}Schema Definition
Field Specifications
Required Fields
start
String
Start date/time in ISO format
Must be valid ISO date string
end
String
End date/time in ISO format
Must be valid ISO date string, must be after start
type
String
Type of absence
Must be one of: 'vacation', 'holiday', 'break'
timeZone
String
IANA timezone identifier
Must be valid timezone string
Optional Fields
note
String
Description or notes about the absence
null
entireBusiness
Boolean
Whether this affects the entire business
false
members
ObjectId[]
References to assigned members
[]
memberIds
String[]
Member IDs as strings
[]
locations
LocationSchema[]
Affected locations
[]
System Fields
_id
ObjectId
Primary key
Yes
meta
MetaSchema
Metadata information
Partial
stateHistory
StateHistorySchema[]
State change tracking
Yes
createdAt
Date
Creation timestamp
Yes
updatedAt
Date
Last modification timestamp
Yes
Embedded Schemas
LocationSchema
MetaSchema
StateHistorySchema
Relationships
Member Relationship
Type: One-to-Many (Absence โ Members)
Implementation: Array of ObjectId references
Collection:
memberLookup: Populated during queries when member details are needed
Location Relationship
Type: Embedded Documents
Implementation: Array of LocationSchema subdocuments
Storage: Denormalized within absence document
Indexing Strategy
Primary Indexes
Composite Indexes
Query Patterns
Common Queries
Find Absences by Date Range
Find Member-Specific Absences
Paginated Query with Population
Repository Implementation
AbsenceRepository
The repository class extends BaseRepository and implements IAbsenceRepository:
Key Repository Methods
Standard CRUD Operations
createItem(absence: IAbsence): Promise<IAbsence>updateItem(id: string, absence: IAbsence): Promise<IAbsence>findById(id: string): Promise<IAbsence | null>deleteItem(id: string): Promise<void>(soft delete)
Specialized Queries
getAbsencesWithFilter(params): Promise<ISlot[]>findByDateRange(start: string, end: string): Promise<IAbsence[]>findByMember(memberId: string): Promise<IAbsence[]>
Data Consistency
Soft Delete Pattern
Absences use soft deletion through the state history mechanism:
State History Tracking
All state changes are tracked in the stateHistory array:
Initial state: 'active'
Soft delete: 'deleted'
Future states: 'archived', 'suspended', etc.
Query Filtering
Non-deleted records are filtered using aggregation expressions:
Multi-Tenancy
Tenant Isolation
Data isolation is achieved through the meta.tenantId field:
All queries must include tenant filter
Indexes include
meta.tenantIdfor performanceApplication layer enforces tenant boundary
Tenant-Aware Queries
Performance Considerations
Query Optimization
Index Usage: Ensure queries use appropriate indexes
Projection: Select only needed fields
Population: Use selective field population
Aggregation: Use aggregation pipelines for complex queries
Scaling Strategies
Sharding: Consider sharding by
meta.tenantIdRead Replicas: Use read replicas for query-heavy operations
Caching: Implement Redis caching for frequently accessed data
Archive Strategy: Archive old absences to separate collection
Data Migration
Schema Evolution
When schema changes are needed:
Backward Compatible: Add optional fields
Migration Scripts: Create scripts for data transformation
Versioning: Use
meta.versionfor schema versioningRollback: Maintain rollback procedures
Example Migration Script
Backup and Recovery
Backup Strategy
Regular Snapshots: Daily MongoDB snapshots
Point-in-Time Recovery: Enable oplog for PITR
Cross-Region Replication: For disaster recovery
Testing: Regular backup restoration testing
Data Retention
Active Data: Keep in primary collection
Archived Data: Move to archive collection after retention period
Deleted Data: Hard delete after legal retention requirements
Monitoring and Alerts
Database Metrics
Query performance
Index usage statistics
Document growth rate
Connection pool utilization
Alert Conditions
Slow queries (>100ms)
Index misses
High memory usage
Replication lag
Security Considerations
Data Protection
Encryption at Rest: Enable MongoDB encryption
Encryption in Transit: Use TLS for connections
Field-Level Encryption: For sensitive data
Access Control: Role-based database access
Audit Trail
State history provides audit trail for:
Who modified the absence
When changes occurred
What the previous state was
Reason for changes
Last updated
Was this helpful?