Weather alerts can be critical for user safety and business operations. Whether you’re building a mobile app, web dashboard, or IoT system, integrating real-time weather alerts ensures your users stay informed about severe weather conditions. This tutorial walks through building a complete weather alert notification system using WeatherAPI’s alerts endpoint.
Understanding WeatherAPI’s Alerts Endpoint
The /alerts.json endpoint provides government-issued weather alerts from meteorological agencies worldwide. These include severe weather warnings, watches, and advisories for tornadoes, hurricanes, floods, extreme temperatures, and more.
GET https://api.weatherapi.com/v1/alerts.json?key=YOUR_API_KEY&q=Miami,FL
The response includes alert severity levels, effective dates, descriptions, and issuing authorities—everything needed to build intelligent notification logic.
Building the Alert Monitoring System
Let’s create a Node.js service that monitors multiple locations and sends notifications when new alerts are detected:
const axios = require('axios');
const nodemailer = require('nodemailer');
class WeatherAlertMonitor {
constructor(apiKey, locations) {
this.apiKey = apiKey;
this.locations = locations;
this.alertHistory = new Map();
this.emailTransporter = this.setupEmailTransporter();
}
async checkAlerts() {
for (const location of this.locations) {
try {
const response = await axios.get(
`https://api.weatherapi.com/v1/alerts.json`,
{
params: {
key: this.apiKey,
q: location
}
}
);
const alerts = response.data.alerts?.alert || [];
await this.processAlerts(location, alerts);
} catch (error) {
console.error(`Error fetching alerts for ${location}:`, error.message);
}
}
}
async processAlerts(location, alerts) {
const locationHistory = this.alertHistory.get(location) || [];
const newAlerts = alerts.filter(alert =>
!locationHistory.some(stored => stored.id === alert.id)
);
if (newAlerts.length > 0) {
console.log(`${newAlerts.length} new alerts for ${location}`);
for (const alert of newAlerts) {
await this.sendNotification(location, alert);
}
// Update history
this.alertHistory.set(location, alerts);
}
}
}
Smart Alert Filtering and Prioritization
Not all alerts require immediate attention. Implement severity-based filtering to reduce notification fatigue:
filterAlertsBySeverity(alerts, minSeverity = 'Moderate') {
const severityLevels = {
'Minor': 1,
'Moderate': 2,
'Severe': 3,
'Extreme': 4
};
return alerts.filter(alert => {
const alertSeverity = severityLevels[alert.severity] || 0;
const threshold = severityLevels[minSeverity] || 2;
return alertSeverity >= threshold;
});
}
categorizeAlerts(alerts) {
return alerts.reduce((categories, alert) => {
const category = this.getAlertCategory(alert.event);
if (!categories[category]) categories[category] = [];
categories[category].push(alert);
return categories;
}, {});
}
getAlertCategory(event) {
const categories = {
'storm': ['Tornado', 'Hurricane', 'Thunderstorm'],
'temperature': ['Heat', 'Cold', 'Freeze'],
'precipitation': ['Flood', 'Snow', 'Ice'],
'wind': ['Wind', 'Gale']
};
for (const [category, events] of Object.entries(categories)) {
if (events.some(e => event.toLowerCase().includes(e.toLowerCase()))) {
return category;
}
}
return 'other';
}
Multi-Channel Notification System
Build a flexible notification system supporting email, SMS, push notifications, and webhooks:
class NotificationManager {
constructor() {
this.channels = new Map();
}
addChannel(name, handler) {
this.channels.set(name, handler);
}
async sendNotification(alert, location, channels = ['email']) {
const message = this.formatAlertMessage(alert, location);
const promises = channels.map(async channel => {
const handler = this.channels.get(channel);
if (handler) {
try {
await handler(message, alert);
console.log(`Alert sent via ${channel}`);
} catch (error) {
console.error(`Failed to send via ${channel}:`, error.message);
}
}
});
await Promise.allSettled(promises);
}
formatAlertMessage(alert, location) {
return {
subject: `Weather Alert: ${alert.event} in ${location}`,
body: `
SEVERITY: ${alert.severity}
EVENT: ${alert.event}
AREA: ${alert.areas}
EFFECTIVE: ${alert.effective}
EXPIRES: ${alert.expires}
DESCRIPTION:
${alert.desc}
INSTRUCTION:
${alert.instruction}
`,
priority: this.getPriority(alert.severity)
};
}
}
Real-Time Monitoring with Scheduled Checks
Implement periodic monitoring with exponential backoff for API reliability:
class AlertScheduler {
constructor(monitor, interval = 300000) { // 5 minutes default
this.monitor = monitor;
this.interval = interval;
this.isRunning = false;
this.retryCount = 0;
}
start() {
if (this.isRunning) return;
this.isRunning = true;
console.log('Weather alert monitoring started');
this.schedule();
}
async schedule() {
if (!this.isRunning) return;
try {
await this.monitor.checkAlerts();
this.retryCount = 0; // Reset on success
setTimeout(() => this.schedule(), this.interval);
} catch (error) {
console.error('Monitoring cycle failed:', error.message);
// Exponential backoff
const delay = Math.min(300000, 1000 * Math.pow(2, this.retryCount));
this.retryCount++;
setTimeout(() => this.schedule(), delay);
}
}
stop() {
this.isRunning = false;
console.log('Weather alert monitoring stopped');
}
}
// Usage
const monitor = new WeatherAlertMonitor(
'YOUR_API_KEY',
['New York,NY', 'Miami,FL', 'Los Angeles,CA']
);
const scheduler = new AlertScheduler(monitor);
scheduler.start();
Production Considerations
For production deployment, consider implementing alert deduplication using unique alert IDs, rate limiting to stay within WeatherAPI’s generous limits, persistent storage for alert history, and user preference management for notification types and timing.
WeatherAPI’s alerts endpoint provides reliable access to official weather warnings with 200ms average response times and 99.9% uptime. The free plan includes 100,000 calls monthly—sufficient for monitoring hundreds of locations.
Ready to build your weather alert system? Sign up for your free WeatherAPI key and start protecting your users with real-time weather intelligence. No credit card required for the free tier.
