Eloomen is a production-ready, enterprise-grade digital vault platform that enables secure, relationship-based data sharing with sophisticated time-based and conditional access policies. Built from the ground up with security-first principles, Eloomen solves critical real-world problems around digital estate planning, family data sharing, and conditional information access.
- Policy-Driven Architecture: Sophisticated time-based release policies (immediate, scheduled, expiry-based, manual)
- Relationship-Based Access Control: Dynamic, configurable groups with granular permissions
- Multi-Type Data Support: Documents, passwords, crypto wallets, notes, and links โ all encrypted
- Enterprise Security: End-to-end encryption, audit logging, JWT with refresh tokens, device verification
- Real-Time Notifications: Comprehensive notification system with email and in-app notifications
- Production-Ready: Automated migrations, CI/CD pipelines, comprehensive error handling
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ Next.js 16 Frontend โ
โ React 19, TypeScript, TailwindCSS, WebCrypto API โ
โ - Client-side encryption โ
โ - JWT token management โ
โ - Real-time notifications โ
โโโโโโโโโโโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ REST API (JWT Auth)
โ HTTPS/TLS
โโโโโโโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ASP.NET Core 9 Backend API โ
โ - Controllers (API Endpoints) โ
โ - Service Layer (Business Logic) โ
โ - Entity Framework Core (ORM) โ
โ - Policy-based Authorization โ
โโโโโโโโโฌโโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโ
โ โ โ
โโโโโโโโโผโโโโโ โโโโโโโโโผโโโโโ โโโโโโโโผโโโโโโโโโโโ
โPostgreSQL โ โ S3 Bucket โ โ SendGrid Email โ
โ(Supabase) โ โ (Storage) โ โ (Notifications)โ
โ โ โ โ โ โ
โ - 24 Tablesโ โ - Documents โ โ - Transactionalโ
โ - Triggers โ โ - Signed URLsโ โ - Templates โ
โ - Functionsโ โ โ โ โ
โโโโโโโโโโโโโโ โโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ CLIENT LAYER โ
โ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โ
โ โ Pages โ โ Components โ โ Contexts โ โ API Client โ โ
โ โ (Next.js) โ โ (React) โ โ (Auth) โ โ (HTTP) โ โ
โ โโโโโโโโฌโโโโโโโโ โโโโโโโโฌโโโโโโโ โโโโโโโโฌโโโโโโ-โ โโโโโโโโฌโโโโโโโโ โ
โ โ โ โ โ โ
โ โโโโโโโโโโโโโโโโโโโดโโโโโโโโโโโโโโ-โโดโโโโโโโโโโโโโโโ--โ โ
โ โ JWT Auth โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ CONTROLLER LAYER โ
โ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โ
โ โ Account โ โ Vault โ โ VaultItem โ โ Notification โ โ
โ โ Controller โ โ Controller โ โ Controller โ โ Controller โ โ
โ โโโโโโโโฌโโโโโโโโ โโโโโโโโฌโโโโโโโ โโโโโโโโฌโโโโโโโโ โโโโโโโโฌโโโโโโโโ โ
โ โ โ โ โ โ
โโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโ
โ โ โ โ
โโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโ
โ SERVICE LAYER โ
โ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โ
โ โ Token โ โ Vault โ โ VaultItem โ โ Notification โ โ
โ โ Service โ โ Service โ โ Service โ โ Service โ โ
โ โโโโโโโโฌโโโโโโโโ โโโโโโโโฌโโโโโโโโ โโโโโโโโฌโโโโโโโโ โโโโโโโโฌโโโโโโโโ โ
โ โ โ โ โ โ
โ โโโโโโโโผโโโโโโโโ โโโโโโโโโผโโโโโโโโ โโโโโโโโผโโโโโโโโ โโโโโโโโผโโโโโโโโ โ
โ โ Device โ โ Email โ โ Encryption โ โ S3 โ โ
โ โ Service โ โ Service โ โ Service โ โ Service โ โ
โ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โ
โโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ
โโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ENTITY FRAMEWORK CORE (ORM) โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ ApplicationDBContext โ โ
โ โ - DbSet<User> โ โ
โ โ - DbSet<Vault> โ โ
โ โ - DbSet<VaultItem> โ โ
โ โ - DbSet<Notification> โ โ
โ โ - ... (24 tables) โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ POSTGRESQL DATABASE โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ 24 Database Tables โ โ
โ โ โข Users, Roles, UserRoles, UserClaims, RoleClaims โ โ
โ โ โข UserDevices, RefreshTokens, VerificationCodes โ โ
โ โ โข Vaults, VaultMembers, VaultInvites, VaultPolicies โ โ
โ โ โข VaultItems, VaultItemVisibilities โ โ
โ โ โข VaultDocuments, VaultPasswords, VaultNotes โ โ
โ โ โข VaultLinks, VaultCryptoWallets โ โ
โ โ โข VaultLogs, AccountLogs, Notifications โ โ
โ โ โข UserLogins, UserTokens โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ PostgreSQL Triggers & Functions โ โ
โ โ โข notify_vault_released() - Auto-notify on vault release โ โ
โ โ โข vault_release_notification_trigger - Monitors ReleaseStatus changes โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ NOTIFICATION FLOW โ
โ โ
โ Event Triggered (Vault Release, Item Edit, Invite, etc.) โ
โ โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ โ โ
โ โโโโโโโโผโโโโโโโโโโโ โโโโโโโโโโผโโโโโโโ โ
โ โ Service Layer โ โ PostgreSQL โ โ
โ โ (Business Logic) โ โ Trigger โ โ
โ โโโโโโโโฌโโโโโโโโโโโโ โโโโโโโโโโฌโโโโโโโโ โ
โ โ โ โ
โ โโโโโโโโผโโโโโโโโโโโ โโโโโโโโโโผโโโโโโโ โ
โ โ Email Service โ โ Notifications โ โ
โ โ (SendGrid) โ โ Table โ โ
โ โ โ โโโโโโโโโโฌโโโโโโโโ โ
โ โ โข Send Email โ โ โ
โ โ โข HTML Templatesโ โ โ
โ โโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโผโโโโโโโ โ
โ โ Notification โ โ
โ โ Service โ โ
โ โ (Create/Read) โ โ
โ โโโโโโโโโโฌโโโโโโโโ โ
โ โ โ
โ โโโโโโโโโโผโโโโโโโ โ
โ โ Frontend โ โ
โ โ (Real-time UI)โ โ
โ โโโโโโโโโโโโโโโโโ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ SERVICE INTERFACES โ
โ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โ
โ โ ITokenServiceโ โ IVaultServiceโ โIVaultItem โ โINotification โ โ
โ โ โ โ โ โService โ โService โ โ
โ โโโโโโโโฌโโโโโโโโ โโโโโโโโฌโโโโโโโ โโโโโโโโฌโโโโโโโโ โโโโโโโโฌโโโโโโโโ โ
โ โ โ โ โ โ
โ โโโโโโโโผโโโโโโโโ โโโโโโโโโผโโโโโโโโ โโโโโโโโผโโโโโโโโ โโโโโโโโผโโโโโโโโ โ
โ โ TokenService โ โ VaultService โ โVaultItem โ โNotification โ โ
โ โ โ โ โ โService โ โService โ โ
โ โ โข JWT Gen โ โ โข CRUD Ops โ โ โข CRUD Ops โ โ โข Create โ โ
โ โ โข Refresh โ โ โข Policy Mgmt โ โ โข Encryption โ โ โข Mark Read โ โ
โ โ โข Validation โ โ โข Invites โ โ โข Permissionsโ โ โข Delete โ โ
โ โ โ โ โข Members โ โ โข S3 Upload โ โ โข Query โ โ
โ โโโโโโโโโโโโโโโโ โโโโโโโโโฌโโโโโโโโโ โโโโโโโโฌโโโโโโโโ โโโโโโโโโโโโโโโโ โ
โ โ โ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โ โ SUPPORTING SERVICES โ โ
โ โ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโ โ
โ โ โ IEmailServiceโ โIEncryption โ โ IS3Service โ โIDeviceServiceโโ โ
โ โ โ โ โService โ โ โ โ โโ โ
โ โ โ โข SendGrid โ โ โข AES-256 โ โ โข Upload โ โ โข Fingerprintโโ โ
โ โ โ โข Templates โ โ โข Encrypt โ โ โข Download โ โ โข Verify โโ โ
โ โ โ โข Notify โ โ โข Decrypt โ โ โข Delete โ โ โข Manage โโ โ
โ โ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโ โ
โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
- Framework: Next.js 16.1.1 (App Router, Server Components)
- Language: TypeScript 5.0+ (strict mode)
- UI: React 19.2.3, TailwindCSS 4.0
- State Management: React Context API, Custom hooks
- Authentication: JWT with automatic token refresh
- Encryption: WebCrypto API for client-side encryption
- HTTP Client: Custom API client with retry logic and error handling
- Notifications: Real-time notification system with polling and badge counts
- Framework: ASP.NET Core 9.0
- ORM: Entity Framework Core 9.0 (Code-First migrations)
- Database: PostgreSQL 15+ (via Supabase)
- Authentication: ASP.NET Core Identity + Custom JWT implementation
- Authorization: Policy-based with role hierarchy (Owner โ Admin โ Member)
- File Storage: S3 bucket for document storage
- Email: SendGrid integration for transactional emails
- API Documentation: Swagger/OpenAPI
- Notifications: In-app notification system with PostgreSQL triggers
- Database: Supabase (PostgreSQL + Storage)
- Object Storage: S3 bucket
- CI/CD: GitHub Actions (build, test, deploy)
- Migrations: Automatic EF Core migrations on startup
- Logging: Structured logging with ILogger
- Error Handling: Global exception handling, custom error responses
- Database Triggers: PostgreSQL functions for automated notifications
Multi-Layer Security Model:
-
JWT Authentication
- Short-lived access tokens (15 minutes)
- Long-lived refresh tokens (stored in HTTP-only cookies)
- Automatic token rotation on refresh
- Security stamp validation for token revocation
-
Device Verification
- Device fingerprinting for new device detection
- Email-based device verification codes
- Device management dashboard
-
Role-Based Access Control (RBAC)
- Owner: Full control (create, edit, delete, manage members, transfer ownership)
- Admin: Manage items and members (cannot delete vault or transfer ownership)
- Member: View and edit items (permission-based)
-
Policy-Based Access Control
- Vault-level policies override member access
- Time-based release policies
- Expiry-based access revocation
- Manual release triggers
- At Rest: All sensitive data encrypted before database storage
- In Transit: HTTPS/TLS for all API communications
- Client-Side: WebCrypto API for encryption before transmission
- Secrets: Passwords, crypto keys, and sensitive notes encrypted with AES-256
- Comprehensive Audit Logging: All vault operations logged (create, update, delete, invite, member changes)
- Account Activity Logs: User authentication, device changes, profile updates
- Immutable Logs: Timestamped, user-attributed audit trail
- Data Retention: Configurable retention policies
- Change Tracking: Detailed field-level change tracking for vault items
The application uses 24 PostgreSQL tables organized into the following categories:
- Users - Core user accounts with email, username, security stamps
- Roles - System roles (Admin, User)
- UserRoles - Many-to-many relationship between users and roles
- UserClaims - Custom claims for users
- RoleClaims - Custom claims for roles
- UserLogins - External login providers
- UserTokens - External authentication tokens
- UserDevices - Registered devices with fingerprinting
- RefreshTokens - JWT refresh tokens linked to devices
- VerificationCodes - Email/device verification codes
- Vaults - Main vault entities with owner relationships
- VaultMembers - Vault membership with privileges (Owner/Admin/Member)
- VaultInvites - Invitation system with tokens and expiration
- VaultPolicies - Policy configuration (Immediate/TimeBased/ExpiryBased/ManualRelease)
- VaultItems - Base vault item entity (polymorphic)
- VaultItemVisibilities - Granular permissions per item per member
- VaultDocuments - Document items with S3 object keys
- VaultPasswords - Password items (encrypted)
- VaultNotes - Note items (encrypted)
- VaultLinks - Link/bookmark items
- VaultCryptoWallets - Cryptocurrency wallet items (encrypted)
- VaultLogs - Comprehensive vault operation audit logs
- AccountLogs - User account activity logs
- Notifications - In-app notification system
Users (1) โโโโโโ< (N) Vaults (Owner)
โ โ
โ โโโ< (N) VaultMembers >โโ (N) Users
โ โ
โ โโโ< (N) VaultInvites
โ โ
โ โโโ< (1) VaultPolicies
โ โ
โ โโโ< (N) VaultItems
โ โ
โ โโโ< (1) VaultDocuments
โ โโโ< (1) VaultPasswords
โ โโโ< (1) VaultNotes
โ โโโ< (1) VaultLinks
โ โโโ< (1) VaultCryptoWallets
โ โ
โ โโโ< (N) VaultItemVisibilities >โโ (N) VaultMembers
โ
โโโ< (N) UserDevices
โ โโโ< (N) RefreshTokens
โ
โโโ< (N) VerificationCodes
โโโ< (N) AccountLogs
โโโ< (N) Notifications
VaultPolicies โโ> PostgreSQL Trigger โโ> Notifications (Auto-create on release)
- Soft Deletes: Vaults and items support 30-day recovery window
- Cascade Deletes: Proper foreign key constraints with cascade rules
- Indexing: Optimized indexes on frequently queried fields (userId, vaultId, status, timestamps)
- Transactions: Critical operations wrapped in database transactions
- Migration Strategy: Code-first migrations with automatic application
- Database Triggers: PostgreSQL functions for automated notification creation on vault release
- Polymorphic Items: Single VaultItems table with one-to-one relationships to specific item types
Sophisticated policy system supporting multiple release strategies:
- Immediate: Instant access upon vault creation
- TimeBased: Scheduled release at a future date/time
- ExpiryBased: Access expires after a set date
- ManualRelease: Requires explicit owner action
Implementation: Policy evaluation runs on every vault access, automatically updating release status based on current time and policy rules. PostgreSQL triggers automatically create notifications when vaults are released.
Each vault item can have different visibility rules per member:
- View: Read-only access
- Edit: Full edit capabilities
- Inherit: Default vault-level permissions
Implementation: VaultItemVisibility junction table enables fine-grained access control without performance overhead. Owners always have Edit permission and are excluded from visibility checks.
Robust invitation workflow with:
- Email-based invitations with secure tokens
- Expiration handling (default 7 days, configurable)
- Status tracking (Pending โ Sent โ Accepted/Cancelled/Expired)
- Automatic member creation on acceptance
- Resend and cancel capabilities
- Email notifications to vault owner when invites are sent
- Notifications to both inviter and invitee when invites expire
Security: Tokens hashed with SHA-256 before storage, never stored in plaintext.
- S3 Bucket Integration: Secure document storage with signed URLs
- Signed URLs: Time-limited download URLs for secure file access
- Metadata Tracking: File size, MIME type, original filename
- Cleanup: Automatic file deletion on item/vault deletion
Comprehensive notification system with multiple channels:
- In-App Notifications: Real-time notification center with unread badges
- Email Notifications: SendGrid integration for critical events
- PostgreSQL Triggers: Automated notification creation on vault release
- Notification Types:
- Vault released
- Vault policy changed
- Vault deleted
- Vault item edited/deleted (to owner)
- Invite sent/accepted/expired
- Password changed
- Account deleted
Implementation: Notifications are created both programmatically in services and automatically via database triggers for vault release events.
Comprehensive email notification system covering:
- Account Events: Email verification, password changes, account deletion
- Vault Events: Vault released, policy changed, vault deleted
- Item Events: Item edited/deleted by other members (notifies owner)
- Invite Events: Invite sent, accepted, expired
- Security Events: Device verification, password reset
Implementation: SendGrid service with HTML email templates, dark mode styling, and professional branding.
Comprehensive audit trail:
- VaultLogs: All vault operations (create, update, delete, invite, member changes)
- AccountLogs: User authentication, device changes, profile updates
- Change Tracking: Field-level change tracking for vault items (title, description, permissions, etc.)
- Immutable Logs: Timestamped, user-attributed audit trail
- Custom Error Classes:
SessionExpiredErrorfor graceful auth failures - Retry Logic: Automatic token refresh on 401 responses
- User-Friendly Messages: Transformed technical errors into actionable user feedback
- Logging: Comprehensive error logging with context for debugging
- TypeScript: Strict mode enabled, full type safety
- ESLint: Next.js recommended rules
- Code Organization: Feature-based folder structure
- Separation of Concerns: Clear boundaries between UI, business logic, and data access
- RESTful Principles: Standard HTTP methods and status codes
- DTO Pattern: Separate request/response DTOs for type safety
- Validation: Model validation with ASP.NET Core Data Annotations
- Error Responses: Consistent error response format
- Database Queries: Eager loading with
.Include()to prevent N+1 queries - Indexing: Comprehensive indexes on foreign keys, status fields, and timestamps
- Pagination Ready: Architecture supports pagination (future enhancement)
- Caching Strategy: Ready for Redis integration (future)
- Frontend: Code splitting, lazy loading, optimized bundle size
- Notification Polling: Efficient 30-second polling for new notifications
The project includes comprehensive backend testing using xUnit and Moq for .NET 9.0.
- .NET 9 SDK (required for running tests)
- PostgreSQL (for integration tests, can use in-memory database for unit tests)
server/
โโโ Tests/
โ โโโ Controllers/ # Controller integration tests
โ โ โโโ AccountControllerTests.cs
โ โ โโโ VaultControllerTests.cs
โ โ โโโ VaultItemControllerTests.cs
โ โ โโโ NotificationControllerTests.cs
โ โ โโโ ContactControllerTests.cs
โ โ โโโ HealthControllerTests.cs
โ โโโ Services/ # Service layer unit tests
โ โ โโโ TokenServiceTests.cs
โ โ โโโ VaultServiceTests.cs
โ โ โโโ VaultItemServiceTests.cs
โ โ โโโ NotificationServiceTests.cs
โ โ โโโ EncryptionServiceTests.cs
โ โ โโโ DeviceServiceTests.cs
โ โ โโโ VaultServiceExtendedTests.cs
โ โโโ Helpers/ # Test utilities and helpers
โ โ โโโ TestHelpers.cs
โ โโโ server.Tests.csproj # Test project file
cd server
dotnet test Tests/server.Tests.csproj --configuration Release --verbosity normalcd server
dotnet test Tests/server.Tests.csproj \
--configuration Release \
--collect:"XPlat Code Coverage" \
--results-directory:./coveragedotnet test Tests/server.Tests.csproj --filter "FullyQualifiedName~AccountControllerTests"dotnet test Tests/server.Tests.csproj --filter "FullyQualifiedName~AccountControllerTests.Register_WithValidData_CreatesUser"โ All Tests Passing: 117 tests, 0 failures
Controller Tests (6 test classes, ~40 tests)
- โ
AccountControllerTests- Authentication, registration, profile management - โ
VaultControllerTests- Vault CRUD, member management, invites, policies - โ
VaultItemControllerTests- Item CRUD, permissions, restore operations - โ
NotificationControllerTests- Notification retrieval, marking as read, deletion - โ
ContactControllerTests- Contact form submission - โ
HealthControllerTests- Health check endpoints
Service Tests (8 test classes, ~77 tests)
- โ
TokenServiceTests- JWT token generation, validation, refresh tokens - โ
VaultServiceTests- Vault business logic, permissions, CRUD operations - โ
VaultServiceExtendedTests- Advanced vault operations (invites, transfers, policies) - โ
VaultItemServiceTests- Item operations, permissions, encryption - โ
VaultItemServiceExtendedTests- Advanced item operations (restore, permissions) - โ
NotificationServiceTests- Notification creation, retrieval, updates - โ
EncryptionServiceTests- AES-256 encryption/decryption, Unicode support - โ
DeviceServiceTests- Device fingerprinting, verification, management
Tests are automatically run in GitHub Actions on every push and pull request:
# .github/workflows/ci.yml
- name: Run tests
run: dotnet test server/Tests/server.Tests.csproj --no-restore --configuration Release --verbosity normal- Trigger: Push to
main,develop,masterbranches or pull requests - Environment: Ubuntu Latest with .NET 9.0.x
- Test Results: Uploaded as artifacts for review
- Status: All tests must pass for CI to succeed
- Arrange-Act-Assert (AAA): Standard test structure
- Mocking: Moq framework for dependencies (database, external services)
- In-Memory Database: EF Core InMemory provider for fast unit tests
- Test Fixtures: Reusable test data and setup helpers
- Integration Tests: Full controller tests with mocked services
[Fact]
public async Task Register_WithValidData_CreatesUser()
{
// Arrange
var registerDto = new RegisterDTO { /* ... */ };
// Act
var result = await _controller.Register(registerDto);
// Assert
Assert.NotNull(result);
Assert.Equal(200, ((ObjectResult)result).StatusCode);
}- Test Helpers:
TestHelpers.csprovides utilities for creating test data - Isolated Tests: Each test is independent with its own database context
- Cleanup: Automatic cleanup after each test execution
- Test Data: Realistic test scenarios covering edge cases
- โ Controllers: 100% endpoint coverage
- โ Services: Core business logic fully tested
- โ Critical Paths: Authentication, authorization, encryption
- ๐ Integration Tests: API endpoint integration testing
- ๐ E2E Tests: Full user workflow testing (planned)
Always run tests locally before pushing to ensure CI passes:
# Run all tests
cd server
dotnet test Tests/server.Tests.csproj --configuration Release
# Expected output: All 117 tests passing โ
Eloomen/
โโโ client/ # Next.js frontend
โ โโโ app/ # App Router pages
โ โ โโโ components/ # Reusable React components
โ โ โ โโโ ContactModal.tsx
โ โ โ โโโ CreateVaultItemModal.tsx
โ โ โ โโโ NotificationsModal.tsx
โ โ โโโ contexts/ # React Context providers
โ โ โ โโโ AuthContext.tsx
โ โ โโโ lib/ # Utilities, API client
โ โ โ โโโ api.ts # API client with JWT handling
โ โ โโโ dashboard/ # Dashboard page
โ โ โโโ vaults/[id]/ # Vault detail page
โ โ โโโ account/ # Account management
โ โ โโโ login/ # Authentication pages
โ โ โโโ [other routes]/
โ โโโ public/ # Static assets
โ โ โโโ icon.png # Logo
โ โโโ package.json
โ
โโโ server/ # ASP.NET Core backend
โ โโโ Controllers/ # API endpoints
โ โ โโโ AccountController.cs
โ โ โโโ VaultController.cs
โ โ โโโ VaultItemController.cs
โ โ โโโ NotificationController.cs
โ โ โโโ ContactController.cs
โ โโโ Services/ # Business logic layer
โ โ โโโ TokenService.cs
โ โ โโโ VaultService.cs
โ โ โโโ VaultItemService.cs
โ โ โโโ NotificationService.cs
โ โ โโโ EmailService.cs
โ โ โโโ EncryptionService.cs
โ โ โโโ S3Service.cs
โ โ โโโ DeviceService.cs
โ โโโ Interfaces/ # Service contracts
โ โ โโโ ITokenService.cs
โ โ โโโ IVaultService.cs
โ โ โโโ IVaultItemService.cs
โ โ โโโ INotificationService.cs
โ โ โโโ IEmailService.cs
โ โ โโโ IEncryptionService.cs
โ โ โโโ IS3Service.cs
โ โ โโโ IDeviceService.cs
โ โโโ Models/ # Entity models (24 tables)
โ โ โโโ User.cs
โ โ โโโ Vault.cs
โ โ โโโ VaultItem.cs
โ โ โโโ Notification.cs
โ โ โโโ [other models]
โ โโโ Dtos/ # Data transfer objects
โ โ โโโ Account/
โ โ โโโ Vault/
โ โ โโโ VaultItem/
โ โ โโโ Notification/
โ โโโ Data/ # DbContext, migrations
โ โ โโโ ApplicationDBContext.cs
โ โ โโโ Migrations/
โ โ โโโ [migration files including triggers]
โ โโโ Program.cs # Application startup
โ
โโโ README.md
- Node.js 20+ and npm
- .NET 9 SDK
- PostgreSQL 15+ (or Supabase account)
- AWS S3 bucket (for file storage)
- SendGrid account (for emails)
-
Backend Configuration (
server/appsettings.json):{ "ConnectionStrings": { "Default": "PostgreSQL connection string" }, "Jwt": { "Issuer": "Eloomen", "Audience": "EloomenUsers", "SigningKey": "your-secret-key" }, "S3": { "Endpoint": "your-s3-endpoint", "AccessKey": "your-access-key", "SecretKey": "your-secret-key", "BucketName": "your-bucket" }, "SendGrid": { "ApiKey": "your-sendgrid-api-key", "FromEmail": "noreply@eloomen.com", "FromName": "Eloomen" }, "App": { "BaseUrl": "http://localhost:3000" } } -
Frontend Configuration (
.env.local):NEXT_PUBLIC_API_URL=http://localhost:5000/api
Run both server and client separately in different terminals:
# Backend
cd server
dotnet restore
dotnet watch run
# Frontend (new terminal)
cd client
npm install
npm run devThe project includes a complete Docker setup with hot reload for both frontend and backend, making it easy to run the entire application with a single command.
- Docker and Docker Compose installed
.envfile created in the root directory (see setup below)
-
Create a
.envfile in the root directory of the project.Option A: Copy from
appsettings.development.jsonIf you already have
server/appsettings.development.jsonconfigured, you can create the.envfile by converting the JSON structure to environment variables. Use double underscores (__) for nested configuration keys.Option B: Create manually
The
.envfile should contain all environment variables matching the structure ofserver/appsettings.development.json. Use double underscores (__) for nested configuration keys.Example
.envfile:# Database Connection String ConnectionStrings__Default=User Id=postgres.xxx;Password=xxx;Server=xxx;Port=5432;Database=postgres # JWT Configuration Jwt__Issuer=http://localhost:3000 Jwt__Audience=http://localhost:3001 Jwt__SigningKey=your-secret-signing-key-here Jwt__AccessTokenMinutes=15 Jwt__RefreshTokenDays=30 # SendGrid Configuration SendGrid__ApiKey=SG.xxx SendGrid__FromEmail=support@eloomen.com SendGrid__FromName=Eloomen SendGrid__AdminEmail=your-admin-email@example.com # App Configuration App__BaseUrl=http://localhost:3001 App__EmailVerificationPath=/verify-email App__DeviceVerificationPath=/verify-device App__PasswordResetPath=/reset-password App__VerificationCodeExpiration__EmailVerificationMinutes=1440 App__VerificationCodeExpiration__DeviceVerificationMinutes=60 App__VerificationCodeExpiration__PasswordResetMinutes=60 # S3 / Cloudflare R2 Configuration S3__BucketName=eloomen-dev S3__BaseUrl=https://xxx.r2.cloudflarestorage.com S3__Endpoint=https://xxx.r2.cloudflarestorage.com S3__AccessKeyId=xxx S3__SecretAccessKey=xxx # Frontend Configuration NEXT_PUBLIC_API_URL=http://localhost:3000/api
Important Notes:
- The
.envfile is already in.gitignoreand will not be committed to the repository - Variable names use
__(double underscore) for nested configuration (e.g.,ConnectionStrings__Default,Jwt__Issuer) - Copy values from
server/appsettings.development.jsonand convert the JSON structure to environment variable format - For nested objects, use
__to separate levels (e.g.,App__VerificationCodeExpiration__EmailVerificationMinutes)
- The
-
Start all services with Docker Compose:
docker-compose up
This will:
- Build and start both frontend and backend services
- Enable hot reload for both services (changes are reflected immediately)
- Expose frontend on http://localhost:3001
- Expose backend on http://localhost:3000
- Automatically run database migrations on backend startup
- Load all environment variables from the
.envfile
- Port: 3000
- Hot Reload: Enabled via
dotnet watch - Environment: Development
- Database: Automatically runs migrations on startup
- Swagger: Available at http://localhost:3000/swagger
- Port: 3001
- Hot Reload: Enabled via Next.js dev mode
- API URL: http://localhost:3000/api
# Start services
docker-compose up
# Start in detached mode (background)
docker-compose up -d
# Stop services
docker-compose down
# Rebuild after dependency changes
docker-compose build
docker-compose up
# View logs
docker-compose logs -f
# View logs for specific service
docker-compose logs -f backend
docker-compose logs -f frontendBoth services support hot reload out of the box:
- Backend: Changes to
.csfiles automatically triggerdotnet watchto rebuild and restart - Frontend: Changes to
.tsx,.ts, and.cssfiles are automatically reflected in the browser
Source code is mounted as volumes, so you can edit files directly and see changes immediately.
All environment variables are loaded from the .env file in the root directory. The docker-compose.yml uses env_file: - .env to automatically load all variables into both services.
Key Points:
- The
.envfile must be created in the root directory (same level asdocker-compose.yml) - Variable names must match the structure of
appsettings.development.jsonusing__for nesting - The
.envfile is already in.gitignoreand will not be committed to the repository - Both backend and frontend services read from the same
.envfile - Environment variables override
appsettings.development.jsonwhen set
Converting from appsettings.development.json to .env:
| JSON Structure | Environment Variable |
|---|---|
ConnectionStrings.Default |
ConnectionStrings__Default |
Jwt.Issuer |
Jwt__Issuer |
App.VerificationCodeExpiration.EmailVerificationMinutes |
App__VerificationCodeExpiration__EmailVerificationMinutes |
Quick Reference:
- Replace dots (
.) with double underscores (__) - Keep the same structure and nesting
- All string values should be unquoted
- Copy exact values from
appsettings.development.json
- Ensure Docker and Docker Compose are installed and running
- Check that all required environment variables are set in
.env - Verify ports 3000 and 3001 are not already in use
- Ensure source code volumes are properly mounted (check
docker-compose.yml) - Try rebuilding containers:
docker-compose build --no-cache
- Verify
ConnectionStrings__Defaultin.envis correct - Check that your database is accessible from Docker containers
- For local PostgreSQL, use
host.docker.internalinstead oflocalhost - Ensure the connection string format matches:
User Id=xxx;Password=xxx;Server=xxx;Port=5432;Database=postgres
- Verify
NEXT_PUBLIC_API_URLin.envmatches backend URL - Check that both containers are on the same Docker network
- Ensure backend is running and accessible on port 3000
GitHub Actions Workflow:
- Backend Tests: Run 117 unit and integration tests
- Controller tests (Account, Vault, VaultItem, Notification, Contact, Health)
- Service tests (Token, Vault, VaultItem, Notification, Encryption, Device)
- Test results uploaded as artifacts
- Frontend Build & Lint: Build Next.js app and run ESLint
- Build: Compile .NET backend, build Next.js frontend
- Migrations: Automatic database migrations on startup (Railway)
- Deploy: Automated deployment via Railway and Vercel (connected via GitHub)
- API Response Time: < 200ms (p95) for standard operations
- Database Queries: Optimized with proper indexing
- Frontend Bundle: Code-split, lazy-loaded components
- File Upload: Streaming uploads for large files
- Notification Polling: 30-second intervals for efficient updates
- Mobile Apps: Native iOS and Android applications
- Hardware Key Support: FIDO2/WebAuthn integration
- Encrypted Search: Search over encrypted data
- Enterprise Plans: Team management, SSO, advanced policies
- Advanced Analytics: Usage dashboards, access reports
- Real-time Updates: WebSocket support for live notifications
- Unit test coverage (backend services) - โ 117 tests implemented
- Integration tests (API endpoints) - โ Controller tests implemented
- E2E tests (Playwright/Cypress)
- Performance monitoring (Application Insights)
- Rate limiting (API throttling)
- Caching layer (Redis)
- WebSocket for real-time notifications
This is a personal project showcasing full-stack development capabilities. Key areas of focus:
- Security: Industry-standard encryption and authentication
- Scalability: Architecture designed for growth
- Maintainability: Clean code, clear documentation
- User Experience: Intuitive UI, responsive design
Proprietary - All rights reserved
โ
Full-Stack Development: End-to-end implementation from database to UI
โ
Security-First Design: Multi-layer security with encryption, RBAC, and audit logging
โ
Scalable Architecture: Microservices-ready, cloud-native design
โ
Modern Tech Stack: Latest versions of Next.js, .NET, React, TypeScript
โ
Production Practices: CI/CD, automated migrations, error handling, logging
โ
Complex Business Logic: Policy engine, time-based access, granular permissions
โ
API Design: RESTful, well-documented, type-safe
โ
Database Design: Normalized schema, proper relationships, migrations, triggers
โ
Notification System: Comprehensive in-app and email notifications
โ
Change Tracking: Detailed field-level change tracking for audit trails
โ
Test Coverage: 117 comprehensive unit and integration tests
- Backend: ASP.NET Core, Entity Framework Core, PostgreSQL, RESTful APIs
- Frontend: Next.js, React, TypeScript, TailwindCSS, State Management
- Security: JWT, Encryption, RBAC, Audit Logging, Device Verification
- DevOps: GitHub Actions, Docker, Database Migrations
- Architecture: Clean Architecture, DTO Pattern, Service Layer Pattern
- Database: PostgreSQL triggers, functions, complex relationships
- Problem Solving: Complex policy engine, granular permissions, time-based access
- Integration: SendGrid, S3, Supabase
Built with โค๏ธ using Next.js, ASP.NET Core, and PostgreSQL