System Architecture

Understanding Nuraan's technical foundation and data flow

Overview

Nuraan follows a microservices architecture pattern with clear separation between data ingestion, processing, storage, and visualization layers. The system is designed for horizontal scalability and high availability during crisis situations.

┌─────────────────────────────────────────────────────────────────┐
│                         Client Layer                             │
│  ┌──────────────┐  ┌──────────────┐  ┌──────────────┐          │
│  │  Web App     │  │  Mobile App  │  │  API Client  │          │
│  │  (Next.js)   │  │   (Future)   │  │  (External)  │          │
│  └──────────────┘  └──────────────┘  └──────────────┘          │
└─────────────────────────────┬───────────────────────────────────┘
                              │ HTTPS
┌─────────────────────────────▼───────────────────────────────────┐
│                      API Gateway (Caddy)                         │
│                   Automatic TLS, Load Balancing                  │
└─────────────────────────────┬───────────────────────────────────┘
                              │
┌─────────────────────────────▼───────────────────────────────────┐
│                    Application Layer (FastAPI)                   │
│  ┌──────────────┐  ┌──────────────┐  ┌──────────────┐          │
│  │  Auth API    │  │  Geo API     │  │  Analytics   │          │
│  │              │  │              │  │     API      │          │
│  └──────────────┘  └──────────────┘  └──────────────┘          │
└─────────────────────────────┬───────────────────────────────────┘
                              │
┌─────────────────────────────▼───────────────────────────────────┐
│                         Data Layer                               │
│  ┌──────────────────────┐      ┌──────────────────────┐        │
│  │  PostgreSQL/PostGIS  │      │     ClickHouse      │        │
│  │  (Spatial Data)      │      │  (Time-series Data) │        │
│  └──────────────────────┘      └──────────────────────┘        │
└──────────────────────────────────────────────────────────────────┘
        

Component Details

Web Application

Framework:
Next.js 16 with React 19
Map Library:
MapLibre GL + Deck.gl
State Management:
Zustand
Styling:
Tailwind CSS 4.0

API Service

Framework:
FastAPI (Python 3.12)
ASGI Server:
Uvicorn
Connection Pool:
asyncpg
Validation:
Pydantic

Spatial Database

Engine:
PostgreSQL 16
Spatial Extension:
PostGIS 3.4
Data Types:
Geometries, Boundaries
Indexes:
GIST, B-tree

Time-series Database

Engine:
ClickHouse 24.3
Storage:
Column-oriented
Data Types:
CDR Events, Metrics
Compression:
LZ4, ZSTD

Data Flow

1 Data Ingestion

CDR data is ingested through secure API endpoints with validation and anonymization. Raw events are immediately written to ClickHouse for time-series storage while aggregated metrics are computed and stored in PostgreSQL.

2 Real-time Processing

Incoming data triggers real-time aggregation pipelines that compute population density, movement patterns, and service coverage metrics. Spatial joins with administrative boundaries happen at query time for flexibility.

3 Visualization

Processed data is served through RESTful APIs with GeoJSON responses for map rendering. The frontend uses MapLibre GL for efficient WebGL-based rendering of large datasets with client-side interactivity.

Scalability & Performance

10M+
CDR Events/Day

ClickHouse can handle billions of events with sub-second queries

100ms
P95 Response Time

Connection pooling and query optimization ensure fast responses

Horizontal
Scaling Strategy

Stateless API design allows adding nodes as needed

Performance Optimizations for ADM4

Map Rendering Optimizations

  • Viewport-based Loading: Boundaries fetched only for visible area using bbox
  • Dynamic Simplification: Lower zoom levels use simplified geometries (simplify_tolerance)
  • Pan/Zoom Refetch: Data updates on moveend events for efficient loading
  • Lighter Basemap: Tuned raster brightness/contrast/saturation for better readability

Database Optimizations

  • Spatial Indexing: GiST indexes on PostGIS geometry columns
  • Cascade Truncation: TRUNCATE TABLE admin_areas CASCADE for safe reloads
  • Flexible Schema: Same table/API supports both ADM3 (544 areas) and ADM4 (higher detail)

API Optimizations

  • Connection Pooling: Persistent database connections reduce overhead
  • GeoJSON Streaming: Efficient geometry serialization
  • Query Optimization: Spatial queries leverage PostGIS functions