A production-ready proof-of-concept demonstrating modern .NET and Angular patterns with full persistence, user management, and alerting capabilities.
This project implements a real-time cryptocurrency price monitoring system using a decoupled, event-driven architecture. It leverages .NET Aspire for orchestration and features a high-performance .NET backend paired with a reactive, zoneless Angular frontend.
┌─────────────────────────────────────────────────────────────────────────────────────────┐
│ .NET Aspire AppHost │
│ ┌──────────────┐ ┌──────────────┐ ┌─────────────────────────────┐ ┌──────────────┐ │
│ │ Redis │ │ PostgreSQL │ │ Backend API (NET 9) │ │ Angular SPA │ │
│ │ (caching) │ │ (persistence)│ │ Clean Architecture + CQRS │ │ (Zoneless) │ │
│ └──────┬───────┘ └──────┬───────┘ └──────────────┬──────────────┘ └──────┬───────┘ │
└─────────┼─────────────────┼─────────────────────────┼────────────────────────┼──────────┘
└─────────────────┴───────────┬─────────────┘ │
▼ │
[ SignalR / REST ] ◄──────────────────────────┘
- Clean Architecture - Domain, Application, Infrastructure, API layers.
- ASP.NET Core Identity - Secure JWT-based authentication with Refresh Token support for user management.
- EF Core + Npgsql - Relational persistence with PostgreSQL for users, watchlists, and price history.
- Redis - High-performance caching for real-time alerts and state management.
- CQRS with MediatR - Clean separation of read and write operations for scalability.
- System.Threading.Channels - Bounded backpressure management for resilient price streams.
- SignalR - Real-time WebSocket broadcasting of market data to connected clients.
- Polly - Advanced resilience with Retry and Circuit Breaker policies for external dependencies.
- Zoneless Bootstrap - Zero Zone.js overhead for peak rendering performance.
- Angular Signals - Fine-grained reactive state management across all components.
- Signal Store - Structured state management using
@ngrx/signalsfor Auth and Price modules. - Atomic Design - Highly structured and reusable component architecture (Atoms -> Molecules -> Organisms).
- .NET 9.0 SDK or later
- Bun (https://bun.sh)
- Docker (for PostgreSQL and Redis containers via Aspire)
-
Install Bun dependencies for the Angular frontend:
cd frontend bun install -
Run via .NET Aspire (recommended):
cd backend/CryptoSimulator.AppHost dotnet run -
Open the Aspire Dashboard (URL shown in console)
CryptoSimulator/
├── backend/
│ ├── CryptoSimulator.AppHost/ # Aspire orchestration & dependency wiring
│ ├── CryptoSimulator.ServiceDefaults/ # Shared telemetry & resilience config
│ └── src/
│ ├── CryptoSimulator.Domain/ # Aggregates (User, WatchlistItem, CryptoPrice), Value Objects, Events
│ ├── CryptoSimulator.Application/ # CQRS Commands, Queries, Logic Handlers
│ ├── CryptoSimulator.Infrastructure/ # Persistence (EF Core), Caching (Redis), Workers
│ └── CryptoSimulator.Api/ # Minimal APIs, Endpoints, Middleware
│
└── frontend/ # Angular Zoneless SPA
└── src/
└── app/
├── core/ # Global Services, Stores (Auth, Price), Interceptors
├── features/ # Auth & Watchlist functional modules
└── ui/ # UI Components (Atoms, Molecules, Organisms)
| Pattern | Location | Why |
|---|---|---|
| Backpressure | PriceChannel.cs |
Prevents producer from overwhelming consumers in the price stream. |
| CQRS | Application handlers | Decouples read and write logic, enabling independent scaling and optimization. |
| Identity | AddIdentityCore |
Provides standardized, secure user management and token-based auth. |
| Persistence | ApplicationDbContext |
Ensures reliable data storage and history tracking using EF Core and PostgreSQL. |
| Caching | RedisAlertCacheService |
Enables low-latency access and distributed state for real-time alerting. |
| Resilience | PollyPolicies.cs |
Handles transient failures and external service outages gracefully. |
| Zoneless | app.config.ts |
Eliminates change detection overhead by removing Zone.js dependencies. |
| Method | Endpoint | Description |
|---|---|---|
POST |
/api/auth/register |
Register a new user |
POST |
/api/auth/login |
Authenticate and get JWT/Refresh tokens |
POST |
/api/auth/refresh |
Refresh an expired access token |
| Method | Endpoint | Description |
|---|---|---|
GET |
/api/prices |
Get current prices for all tracked assets |
GET |
/api/prices/{symbol} |
Get detailed historical and current data for a specific asset |
WS |
/hubs/prices |
SignalR hub for real-time market updates |
| Method | Endpoint | Description |
|---|---|---|
GET |
/api/watchlist |
Get current user's personalized watchlist |
POST |
/api/watchlist |
Add a specific cryptocurrency symbol to the watchlist |
DELETE |
/api/watchlist/{symbol} |
Remove a symbol from the watchlist |
MIT License - Built for learning purposes and demonstration of high-performance web architecture.