# Backend Utilities Utility modules provide common functionality for spatial calculations, logging, metrics collection, and data processing across the Changemaker Lite platform. ## Utility Modules ### Spatial Utilities **spatial.ts** (`utils/spatial.ts`) Provides geospatial calculations and polygon operations: **Point-in-Polygon** - Ray-casting algorithm for polygon containment - Supports GeoJSON polygon format - Handles holes in polygons - Used for cut assignment ```typescript import { isPointInPolygon } from '../utils/spatial'; const inside = isPointInPolygon( { lat: 43.65, lng: -79.38 }, geoJsonPolygon ); ``` **Haversine Distance** - Calculate distance between two coordinates - Returns distance in kilometers - Great-circle distance calculation ```typescript import { haversineDistance } from '../utils/spatial'; const distance = haversineDistance( { lat: 43.65, lng: -79.38 }, { lat: 43.66, lng: -79.39 } ); // Returns: 1.23 (km) ``` **Bounds Calculation** - Calculate bounding box for set of locations - Returns min/max lat/lng - Used for map centering ```typescript import { calculateBounds } from '../utils/spatial'; const bounds = calculateBounds(locations); // Returns: { minLat, maxLat, minLng, maxLng } ``` **Centroid Calculation** - Calculate center point of locations - Geographic mean of coordinates - Used for map initial center ```typescript import { calculateCentroid } from '../utils/spatial'; const center = calculateCentroid(locations); // Returns: { lat, lng } ``` **GeoJSON Parsing** - Parse GeoJSON geometry to coordinate arrays - Support for Polygon and MultiPolygon - Coordinate validation ### Logging Utilities **logger.ts** (`utils/logger.ts`) Winston-based logging with multiple transports: **Log Levels** - `error` - Error conditions - `warn` - Warning messages - `info` - Informational messages - `http` - HTTP request logs - `debug` - Debug-level messages **Usage** ```typescript import logger from '../utils/logger'; logger.info('Campaign created', { campaignId: 123 }); logger.error('Failed to send email', { error: err.message }); logger.debug('Geocoding result', { lat, lng }); ``` **Features** - JSON formatting for production - Colorized console output for development - File rotation for error logs - Separate error log file - Timestamp on all logs - Request ID tracking ### Metrics Utilities **metrics.ts** (`utils/metrics.ts`) Prometheus metrics collection with 12 custom `cm_*` metrics: **Counter Metrics** - `cm_api_uptime_seconds` - API uptime counter - `cm_canvass_visits_total` - Total canvass visits - `cm_campaign_emails_sent_total` - Total campaign emails - `cm_geocode_requests_total` - Total geocode requests **Gauge Metrics** - `cm_canvass_sessions_active` - Active canvass sessions - `cm_email_queue_size` - Email queue depth - `cm_geocode_queue_size` - Geocode queue depth - `cm_external_service_health` - Service health status (0/1) **Histogram Metrics** - `cm_geocode_duration_seconds` - Geocoding request duration - `http_request_duration_ms` - HTTP request duration **Usage** ```typescript import { metrics } from '../utils/metrics'; // Increment counter metrics.campaignEmailsSent.inc(); // Set gauge metrics.emailQueueSize.set(42); // Observe histogram const end = metrics.geocodeDuration.startTimer(); await geocode(address); end(); ``` **HTTP Metrics** Automatic tracking of: - Request count by method, route, status - Request duration percentiles - Active requests gauge ### Path Validation **path-validator.ts** (`utils/path-validator.ts`) Security utilities for path validation: **Features** - Null byte detection - Path traversal prevention (`../` patterns) - Encoded traversal detection (`%2e%2e`) - Path normalization ```typescript import { validatePath } from '../utils/path-validator'; const safe = validatePath(userInput); if (!safe) { throw new Error('Invalid path'); } ``` ### HTML Sanitization **sanitize.ts** (`utils/sanitize.ts`) XSS prevention utilities: ```typescript import { escapeHtml } from '../utils/sanitize'; const safe = escapeHtml(userInput); // Escapes: < > & " ' to HTML entities ``` ## Utility Functions Summary | Utility | Function | Purpose | |---------|----------|---------| | **Spatial** | | | | | `isPointInPolygon()` | Check if point is inside polygon | | | `haversineDistance()` | Calculate distance between points | | | `calculateBounds()` | Calculate bounding box | | | `calculateCentroid()` | Calculate center point | | | `parseGeoJSON()` | Parse GeoJSON to coordinates | | **Logging** | | | | | `logger.info()` | Log informational message | | | `logger.error()` | Log error message | | | `logger.debug()` | Log debug message | | **Metrics** | | | | | `metrics.*.inc()` | Increment counter | | | `metrics.*.set()` | Set gauge value | | | `metrics.*.startTimer()` | Start histogram timer | | **Security** | | | | | `validatePath()` | Validate file path safety | | | `escapeHtml()` | Sanitize HTML content | ## Configuration Utilities are configured via environment variables: ```bash # Logging LOG_LEVEL=info # Minimum log level NODE_ENV=production # Environment mode # Metrics METRICS_ENABLED=true # Enable Prometheus metrics ``` ## Related Documentation - [Backend Overview](../index.md) - [Observability](../../features/observability/index.md) - [Security](../../deployment/security.md) - [Map Features](../../features/map/index.md) - [Monitoring Stack](../../deployment/monitoring-stack.md)