@dangahagan/weather-mcp 0.2.0 → 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (88) hide show
  1. package/README.md +372 -53
  2. package/dist/config/cache.d.ts +2 -0
  3. package/dist/config/cache.d.ts.map +1 -1
  4. package/dist/config/cache.js +48 -2
  5. package/dist/config/cache.js.map +1 -1
  6. package/dist/config/displayThresholds.d.ts +83 -0
  7. package/dist/config/displayThresholds.d.ts.map +1 -0
  8. package/dist/config/displayThresholds.js +83 -0
  9. package/dist/config/displayThresholds.js.map +1 -0
  10. package/dist/errors/ApiError.d.ts +62 -0
  11. package/dist/errors/ApiError.d.ts.map +1 -0
  12. package/dist/errors/ApiError.js +147 -0
  13. package/dist/errors/ApiError.js.map +1 -0
  14. package/dist/handlers/airQualityHandler.d.ts +11 -0
  15. package/dist/handlers/airQualityHandler.d.ts.map +1 -0
  16. package/dist/handlers/airQualityHandler.js +154 -0
  17. package/dist/handlers/airQualityHandler.js.map +1 -0
  18. package/dist/handlers/alertsHandler.d.ts +11 -0
  19. package/dist/handlers/alertsHandler.d.ts.map +1 -0
  20. package/dist/handlers/alertsHandler.js +82 -0
  21. package/dist/handlers/alertsHandler.js.map +1 -0
  22. package/dist/handlers/currentConditionsHandler.d.ts +11 -0
  23. package/dist/handlers/currentConditionsHandler.d.ts.map +1 -0
  24. package/dist/handlers/currentConditionsHandler.js +231 -0
  25. package/dist/handlers/currentConditionsHandler.js.map +1 -0
  26. package/dist/handlers/forecastHandler.d.ts +13 -0
  27. package/dist/handlers/forecastHandler.d.ts.map +1 -0
  28. package/dist/handlers/forecastHandler.js +337 -0
  29. package/dist/handlers/forecastHandler.js.map +1 -0
  30. package/dist/handlers/historicalWeatherHandler.d.ts +12 -0
  31. package/dist/handlers/historicalWeatherHandler.d.ts.map +1 -0
  32. package/dist/handlers/historicalWeatherHandler.js +188 -0
  33. package/dist/handlers/historicalWeatherHandler.js.map +1 -0
  34. package/dist/handlers/locationHandler.d.ts +11 -0
  35. package/dist/handlers/locationHandler.d.ts.map +1 -0
  36. package/dist/handlers/locationHandler.js +113 -0
  37. package/dist/handlers/locationHandler.js.map +1 -0
  38. package/dist/handlers/marineConditionsHandler.d.ts +11 -0
  39. package/dist/handlers/marineConditionsHandler.d.ts.map +1 -0
  40. package/dist/handlers/marineConditionsHandler.js +154 -0
  41. package/dist/handlers/marineConditionsHandler.js.map +1 -0
  42. package/dist/handlers/statusHandler.d.ts +12 -0
  43. package/dist/handlers/statusHandler.d.ts.map +1 -0
  44. package/dist/handlers/statusHandler.js +106 -0
  45. package/dist/handlers/statusHandler.js.map +1 -0
  46. package/dist/index.js +219 -377
  47. package/dist/index.js.map +1 -1
  48. package/dist/services/noaa.d.ts +24 -1
  49. package/dist/services/noaa.d.ts.map +1 -1
  50. package/dist/services/noaa.js +116 -43
  51. package/dist/services/noaa.js.map +1 -1
  52. package/dist/services/openmeteo.d.ts +110 -3
  53. package/dist/services/openmeteo.d.ts.map +1 -1
  54. package/dist/services/openmeteo.js +568 -112
  55. package/dist/services/openmeteo.js.map +1 -1
  56. package/dist/types/noaa.d.ts +158 -12
  57. package/dist/types/noaa.d.ts.map +1 -1
  58. package/dist/types/openmeteo.d.ts +448 -0
  59. package/dist/types/openmeteo.d.ts.map +1 -1
  60. package/dist/utils/airQuality.d.ts +54 -0
  61. package/dist/utils/airQuality.d.ts.map +1 -0
  62. package/dist/utils/airQuality.js +251 -0
  63. package/dist/utils/airQuality.js.map +1 -0
  64. package/dist/utils/cache.d.ts +11 -4
  65. package/dist/utils/cache.d.ts.map +1 -1
  66. package/dist/utils/cache.js +33 -4
  67. package/dist/utils/cache.js.map +1 -1
  68. package/dist/utils/fireWeather.d.ts +62 -0
  69. package/dist/utils/fireWeather.d.ts.map +1 -0
  70. package/dist/utils/fireWeather.js +168 -0
  71. package/dist/utils/fireWeather.js.map +1 -0
  72. package/dist/utils/logger.d.ts +59 -0
  73. package/dist/utils/logger.d.ts.map +1 -0
  74. package/dist/utils/logger.js +128 -0
  75. package/dist/utils/logger.js.map +1 -0
  76. package/dist/utils/marine.d.ts +38 -0
  77. package/dist/utils/marine.d.ts.map +1 -0
  78. package/dist/utils/marine.js +162 -0
  79. package/dist/utils/marine.js.map +1 -0
  80. package/dist/utils/temperatureConversion.d.ts +12 -0
  81. package/dist/utils/temperatureConversion.d.ts.map +1 -0
  82. package/dist/utils/temperatureConversion.js +17 -0
  83. package/dist/utils/temperatureConversion.js.map +1 -0
  84. package/dist/utils/validation.d.ts +89 -0
  85. package/dist/utils/validation.d.ts.map +1 -0
  86. package/dist/utils/validation.js +177 -0
  87. package/dist/utils/validation.js.map +1 -0
  88. package/package.json +10 -3
@@ -0,0 +1,337 @@
1
+ /**
2
+ * Handler for get_forecast tool
3
+ * Supports both NOAA (US) and Open-Meteo (global) forecast sources
4
+ */
5
+ import { validateCoordinates, validateForecastDays, validateGranularity, validateOptionalBoolean, } from '../utils/validation.js';
6
+ import { logger } from '../utils/logger.js';
7
+ /**
8
+ * Determine if coordinates are within the United States (including Alaska, Hawaii, and territories)
9
+ * Uses bounding box approach for simplicity
10
+ */
11
+ function isInUS(latitude, longitude) {
12
+ // Continental US, Alaska, Hawaii, Puerto Rico, and territories
13
+ const inContinentalUS = latitude >= 24.5 && latitude <= 49.4 && longitude >= -125 && longitude <= -66.9;
14
+ const inAlaska = latitude >= 51 && latitude <= 71.4 && longitude >= -180 && longitude <= -129.9;
15
+ const inHawaii = latitude >= 18.9 && latitude <= 28.5 && longitude >= -178.4 && longitude <= -154.8;
16
+ const inPuertoRico = latitude >= 17.9 && latitude <= 18.5 && longitude >= -67.3 && longitude <= -65.2;
17
+ return inContinentalUS || inAlaska || inHawaii || inPuertoRico;
18
+ }
19
+ /**
20
+ * Extract maximum value from gridpoint data series for the next 24-48 hours
21
+ * @param series - The gridpoint data series to process
22
+ * @param hours - Number of hours to look ahead (default: 48)
23
+ * @param maxEntries - Maximum number of entries to process for defense-in-depth (default: 500 ~ 1 week hourly data)
24
+ */
25
+ function getMaxProbabilityFromSeries(series, hours = 48, maxEntries = 500) {
26
+ if (!series || !series.values || series.values.length === 0) {
27
+ return 0;
28
+ }
29
+ // Defense-in-depth: Add bounds checking to prevent resource exhaustion
30
+ if (series.values.length > maxEntries) {
31
+ logger.warn('Gridpoint series exceeds max entries', {
32
+ length: series.values.length,
33
+ maxEntries,
34
+ securityEvent: true
35
+ });
36
+ // Slice to limit processing
37
+ series.values = series.values.slice(0, maxEntries);
38
+ }
39
+ const now = new Date();
40
+ const futureTime = new Date(now.getTime() + hours * 60 * 60 * 1000);
41
+ let maxValue = 0;
42
+ for (const entry of series.values) {
43
+ // Parse ISO 8601 interval (e.g., "2025-11-06T15:00:00+00:00/PT1H")
44
+ const validTimeStart = new Date(entry.validTime.split('/')[0]);
45
+ if (validTimeStart >= now && validTimeStart <= futureTime && entry.value !== null) {
46
+ maxValue = Math.max(maxValue, entry.value);
47
+ }
48
+ }
49
+ return maxValue;
50
+ }
51
+ /**
52
+ * Format severe weather probabilities for display
53
+ */
54
+ function formatSevereWeather(properties) {
55
+ let output = '';
56
+ let hasData = false;
57
+ output += `\n## ⚠️ Severe Weather Probabilities (Next 48 Hours)\n\n`;
58
+ // Thunder probability
59
+ const thunderProb = getMaxProbabilityFromSeries(properties.probabilityOfThunder);
60
+ if (thunderProb > 0) {
61
+ hasData = true;
62
+ const emoji = thunderProb > 50 ? '🌩️' : thunderProb > 20 ? '⚡' : '🌤️';
63
+ output += `${emoji} **Thunderstorms:** ${thunderProb}% chance\n`;
64
+ }
65
+ // Wind gust probabilities (show highest risk category)
66
+ const windGust60 = getMaxProbabilityFromSeries(properties.potentialOf60mphWindGusts);
67
+ const windGust50 = getMaxProbabilityFromSeries(properties.potentialOf50mphWindGusts);
68
+ const windGust40 = getMaxProbabilityFromSeries(properties.potentialOf40mphWindGusts);
69
+ const windGust30 = getMaxProbabilityFromSeries(properties.potentialOf30mphWindGusts);
70
+ if (windGust60 > 0) {
71
+ hasData = true;
72
+ output += `💨 **Very High Wind Gusts (60+ mph):** ${windGust60}% chance\n`;
73
+ }
74
+ else if (windGust50 > 0) {
75
+ hasData = true;
76
+ output += `💨 **High Wind Gusts (50+ mph):** ${windGust50}% chance\n`;
77
+ }
78
+ else if (windGust40 > 0) {
79
+ hasData = true;
80
+ output += `💨 **Strong Wind Gusts (40+ mph):** ${windGust40}% chance\n`;
81
+ }
82
+ else if (windGust30 > 20) {
83
+ // Only show moderate gusts if probability is significant
84
+ hasData = true;
85
+ output += `💨 **Moderate Wind Gusts (30+ mph):** ${windGust30}% chance\n`;
86
+ }
87
+ // Tropical storm/hurricane winds (if present)
88
+ const tropicalStormProb = getMaxProbabilityFromSeries(properties.probabilityOfTropicalStormWinds);
89
+ const hurricaneProb = getMaxProbabilityFromSeries(properties.probabilityOfHurricaneWinds);
90
+ if (hurricaneProb > 0) {
91
+ hasData = true;
92
+ output += `🌀 **Hurricane-Force Winds (74+ mph):** ${hurricaneProb}% chance\n`;
93
+ }
94
+ else if (tropicalStormProb > 0) {
95
+ hasData = true;
96
+ output += `🌀 **Tropical Storm Winds (39-73 mph):** ${tropicalStormProb}% chance\n`;
97
+ }
98
+ // Lightning activity
99
+ if (properties.lightningActivityLevel && properties.lightningActivityLevel.values && properties.lightningActivityLevel.values.length > 0) {
100
+ const lightningLevels = properties.lightningActivityLevel.values.filter(v => v.value !== null && v.value > 0);
101
+ if (lightningLevels.length > 0) {
102
+ hasData = true;
103
+ const maxLevel = Math.max(...lightningLevels.map(v => v.value || 0));
104
+ const levelDesc = maxLevel >= 4 ? 'Very High' : maxLevel >= 3 ? 'High' : maxLevel >= 2 ? 'Moderate' : 'Low';
105
+ output += `⚡ **Lightning Activity:** ${levelDesc} (Level ${maxLevel})\n`;
106
+ }
107
+ }
108
+ if (!hasData) {
109
+ return null; // No severe weather data to display
110
+ }
111
+ output += `\n*Note: These are probabilistic forecasts and may change. Always monitor local weather alerts for official warnings.*\n`;
112
+ return output;
113
+ }
114
+ export async function handleGetForecast(args, noaaService, openMeteoService) {
115
+ // Validate input parameters with runtime checks
116
+ const { latitude, longitude } = validateCoordinates(args);
117
+ const days = validateForecastDays(args);
118
+ const granularity = validateGranularity(args?.granularity);
119
+ const include_precipitation_probability = validateOptionalBoolean(args?.include_precipitation_probability, 'include_precipitation_probability', true);
120
+ const include_severe_weather = validateOptionalBoolean(args?.include_severe_weather, 'include_severe_weather', false);
121
+ // Get source preference or auto-detect
122
+ const requestedSource = args?.source || 'auto';
123
+ let useNOAA;
124
+ if (requestedSource === 'auto') {
125
+ // Auto-detect based on location (US = NOAA, elsewhere = Open-Meteo)
126
+ useNOAA = isInUS(latitude, longitude);
127
+ }
128
+ else {
129
+ useNOAA = requestedSource === 'noaa';
130
+ }
131
+ // Use NOAA for US locations or if explicitly requested
132
+ if (useNOAA) {
133
+ return await formatNOAAForecast(noaaService, latitude, longitude, days, granularity, include_precipitation_probability, include_severe_weather);
134
+ }
135
+ else {
136
+ // Use Open-Meteo for international locations
137
+ return await formatOpenMeteoForecast(openMeteoService, latitude, longitude, days, granularity, include_precipitation_probability);
138
+ }
139
+ }
140
+ /**
141
+ * Format NOAA forecast data for display
142
+ */
143
+ async function formatNOAAForecast(noaaService, latitude, longitude, days, granularity, include_precipitation_probability, include_severe_weather) {
144
+ // Get forecast data based on granularity
145
+ const forecast = granularity === 'hourly'
146
+ ? await noaaService.getHourlyForecastByCoordinates(latitude, longitude)
147
+ : await noaaService.getForecastByCoordinates(latitude, longitude);
148
+ // Determine how many periods to show
149
+ let periods;
150
+ if (granularity === 'hourly') {
151
+ // For hourly, show up to days * 24 hours
152
+ periods = forecast.properties.periods.slice(0, days * 24);
153
+ }
154
+ else {
155
+ // For daily, show up to days * 2 (day/night periods)
156
+ periods = forecast.properties.periods.slice(0, days * 2);
157
+ }
158
+ // Format the forecast for display
159
+ let output = `# Weather Forecast (${granularity === 'hourly' ? 'Hourly' : 'Daily'})\n\n`;
160
+ output += `**Location:** ${latitude.toFixed(4)}, ${longitude.toFixed(4)}\n`;
161
+ output += `**Elevation:** ${forecast.properties.elevation.value}m\n`;
162
+ if (forecast.properties.updated) {
163
+ output += `**Updated:** ${new Date(forecast.properties.updated).toLocaleString()}\n`;
164
+ }
165
+ output += `**Showing:** ${periods.length} ${granularity === 'hourly' ? 'hours' : 'periods'}\n\n`;
166
+ for (const period of periods) {
167
+ // For hourly forecasts, use the start time as the header since period names are empty
168
+ const periodHeader = granularity === 'hourly' && !period.name
169
+ ? new Date(period.startTime).toLocaleString()
170
+ : period.name;
171
+ output += `## ${periodHeader}\n`;
172
+ output += `**Temperature:** ${period.temperature}°${period.temperatureUnit}`;
173
+ // Add temperature trend if available
174
+ if (period.temperatureTrend && period.temperatureTrend.trim()) {
175
+ output += ` (${period.temperatureTrend})`;
176
+ }
177
+ output += `\n`;
178
+ // Add precipitation probability if requested and available
179
+ if (include_precipitation_probability && period.probabilityOfPrecipitation?.value !== null && period.probabilityOfPrecipitation?.value !== undefined) {
180
+ output += `**Precipitation Chance:** ${period.probabilityOfPrecipitation.value}%\n`;
181
+ }
182
+ output += `**Wind:** ${period.windSpeed} ${period.windDirection}\n`;
183
+ // Add humidity if available (more common in hourly forecasts)
184
+ if (period.relativeHumidity?.value !== null && period.relativeHumidity?.value !== undefined) {
185
+ output += `**Humidity:** ${period.relativeHumidity.value}%\n`;
186
+ }
187
+ output += `**Forecast:** ${period.shortForecast}\n\n`;
188
+ // For daily forecasts, include detailed forecast
189
+ if (granularity === 'daily' && period.detailedForecast) {
190
+ output += `${period.detailedForecast}\n\n`;
191
+ }
192
+ }
193
+ output += `---\n`;
194
+ output += `*Data source: NOAA National Weather Service (US)*\n`;
195
+ // Add severe weather probabilities if requested
196
+ if (include_severe_weather) {
197
+ try {
198
+ const gridpointData = await noaaService.getGridpointDataByCoordinates(latitude, longitude);
199
+ const severeWeatherSection = formatSevereWeather(gridpointData.properties);
200
+ if (severeWeatherSection) {
201
+ output += `\n${severeWeatherSection}`;
202
+ }
203
+ }
204
+ catch (error) {
205
+ // If severe weather data is unavailable, just note it without failing the whole request
206
+ output += `\n*Note: Severe weather probability data is not available for this location.*\n`;
207
+ }
208
+ }
209
+ return {
210
+ content: [
211
+ {
212
+ type: 'text',
213
+ text: output
214
+ }
215
+ ]
216
+ };
217
+ }
218
+ /**
219
+ * Format Open-Meteo forecast data for display
220
+ */
221
+ async function formatOpenMeteoForecast(openMeteoService, latitude, longitude, days, granularity, include_precipitation_probability) {
222
+ // Get forecast data from Open-Meteo
223
+ const forecast = await openMeteoService.getForecast(latitude, longitude, days, granularity === 'hourly');
224
+ let output = `# Weather Forecast (${granularity === 'hourly' ? 'Hourly' : 'Daily'})\n\n`;
225
+ output += `**Location:** ${latitude.toFixed(4)}, ${longitude.toFixed(4)}\n`;
226
+ output += `**Elevation:** ${forecast.elevation}m\n`;
227
+ output += `**Timezone:** ${forecast.timezone}\n`;
228
+ output += `**Forecast Days:** ${days}\n\n`;
229
+ if (granularity === 'hourly' && forecast.hourly) {
230
+ // Format hourly data
231
+ const hourly = forecast.hourly;
232
+ const numHours = Math.min(hourly.time.length, days * 24);
233
+ for (let i = 0; i < numHours; i++) {
234
+ const time = new Date(hourly.time[i]);
235
+ output += `## ${time.toLocaleString()}\n`;
236
+ if (hourly.temperature_2m?.[i] !== undefined) {
237
+ output += `**Temperature:** ${Math.round(hourly.temperature_2m[i])}°F`;
238
+ if (hourly.apparent_temperature?.[i] !== undefined) {
239
+ output += ` (feels like ${Math.round(hourly.apparent_temperature[i])}°F)`;
240
+ }
241
+ output += `\n`;
242
+ }
243
+ if (include_precipitation_probability && hourly.precipitation_probability?.[i] !== undefined) {
244
+ output += `**Precipitation Chance:** ${hourly.precipitation_probability[i]}%\n`;
245
+ }
246
+ if (hourly.precipitation?.[i] !== undefined && hourly.precipitation[i] > 0) {
247
+ output += `**Precipitation:** ${hourly.precipitation[i].toFixed(2)} in\n`;
248
+ }
249
+ if (hourly.wind_speed_10m?.[i] !== undefined) {
250
+ const windDir = hourly.wind_direction_10m?.[i] !== undefined
251
+ ? ` ${getWindDirection(hourly.wind_direction_10m[i])}`
252
+ : '';
253
+ output += `**Wind:** ${Math.round(hourly.wind_speed_10m[i])} mph${windDir}\n`;
254
+ if (hourly.wind_gusts_10m?.[i] !== undefined && hourly.wind_gusts_10m[i] > hourly.wind_speed_10m[i] * 1.2) {
255
+ output += `**Wind Gusts:** ${Math.round(hourly.wind_gusts_10m[i])} mph\n`;
256
+ }
257
+ }
258
+ if (hourly.relative_humidity_2m?.[i] !== undefined) {
259
+ output += `**Humidity:** ${hourly.relative_humidity_2m[i]}%\n`;
260
+ }
261
+ if (hourly.weather_code?.[i] !== undefined) {
262
+ output += `**Conditions:** ${openMeteoService.getWeatherDescription(hourly.weather_code[i])}\n`;
263
+ }
264
+ output += `\n`;
265
+ }
266
+ }
267
+ else if (forecast.daily) {
268
+ // Format daily data with sunrise/sunset
269
+ const daily = forecast.daily;
270
+ const numDays = Math.min(daily.time.length, days);
271
+ for (let i = 0; i < numDays; i++) {
272
+ const date = new Date(daily.time[i]);
273
+ output += `## ${date.toLocaleDateString('en-US', { weekday: 'long', month: 'long', day: 'numeric' })}\n`;
274
+ if (daily.temperature_2m_max?.[i] !== undefined && daily.temperature_2m_min?.[i] !== undefined) {
275
+ output += `**Temperature:** High ${Math.round(daily.temperature_2m_max[i])}°F / Low ${Math.round(daily.temperature_2m_min[i])}°F\n`;
276
+ }
277
+ if (daily.apparent_temperature_max?.[i] !== undefined && daily.apparent_temperature_min?.[i] !== undefined) {
278
+ output += `**Feels Like:** High ${Math.round(daily.apparent_temperature_max[i])}°F / Low ${Math.round(daily.apparent_temperature_min[i])}°F\n`;
279
+ }
280
+ // Include sunrise/sunset data
281
+ if (daily.sunrise?.[i]) {
282
+ const sunrise = new Date(daily.sunrise[i]);
283
+ output += `**Sunrise:** ${sunrise.toLocaleTimeString('en-US', { hour: 'numeric', minute: '2-digit' })}\n`;
284
+ }
285
+ if (daily.sunset?.[i]) {
286
+ const sunset = new Date(daily.sunset[i]);
287
+ output += `**Sunset:** ${sunset.toLocaleTimeString('en-US', { hour: 'numeric', minute: '2-digit' })}\n`;
288
+ }
289
+ if (daily.daylight_duration?.[i] !== undefined) {
290
+ const hours = Math.floor(daily.daylight_duration[i] / 3600);
291
+ const minutes = Math.floor((daily.daylight_duration[i] % 3600) / 60);
292
+ output += `**Daylight Duration:** ${hours}h ${minutes}m\n`;
293
+ }
294
+ if (include_precipitation_probability && daily.precipitation_probability_max?.[i] !== undefined) {
295
+ output += `**Precipitation Chance:** ${daily.precipitation_probability_max[i]}%\n`;
296
+ }
297
+ if (daily.precipitation_sum?.[i] !== undefined && daily.precipitation_sum[i] > 0) {
298
+ output += `**Precipitation:** ${daily.precipitation_sum[i].toFixed(2)} in\n`;
299
+ }
300
+ if (daily.wind_speed_10m_max?.[i] !== undefined) {
301
+ const windDir = daily.wind_direction_10m_dominant?.[i] !== undefined
302
+ ? ` ${getWindDirection(daily.wind_direction_10m_dominant[i])}`
303
+ : '';
304
+ output += `**Wind:** ${Math.round(daily.wind_speed_10m_max[i])} mph${windDir}\n`;
305
+ if (daily.wind_gusts_10m_max?.[i] !== undefined && daily.wind_gusts_10m_max[i] > daily.wind_speed_10m_max[i] * 1.2) {
306
+ output += `**Wind Gusts:** ${Math.round(daily.wind_gusts_10m_max[i])} mph\n`;
307
+ }
308
+ }
309
+ if (daily.weather_code?.[i] !== undefined) {
310
+ output += `**Conditions:** ${openMeteoService.getWeatherDescription(daily.weather_code[i])}\n`;
311
+ }
312
+ if (daily.uv_index_max?.[i] !== undefined) {
313
+ output += `**UV Index:** ${daily.uv_index_max[i].toFixed(1)}\n`;
314
+ }
315
+ output += `\n`;
316
+ }
317
+ }
318
+ output += `---\n`;
319
+ output += `*Data source: Open-Meteo (Global)*\n`;
320
+ return {
321
+ content: [
322
+ {
323
+ type: 'text',
324
+ text: output
325
+ }
326
+ ]
327
+ };
328
+ }
329
+ /**
330
+ * Convert wind direction degrees to cardinal direction
331
+ */
332
+ function getWindDirection(degrees) {
333
+ const directions = ['N', 'NNE', 'NE', 'ENE', 'E', 'ESE', 'SE', 'SSE', 'S', 'SSW', 'SW', 'WSW', 'W', 'WNW', 'NW', 'NNW'];
334
+ const index = Math.round(degrees / 22.5) % 16;
335
+ return directions[index];
336
+ }
337
+ //# sourceMappingURL=forecastHandler.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"forecastHandler.js","sourceRoot":"","sources":["../../src/handlers/forecastHandler.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Handler for get_historical_weather tool
3
+ */
4
+ import { NOAAService } from '../services/noaa.js';
5
+ import { OpenMeteoService } from '../services/openmeteo.js';
6
+ export declare function handleGetHistoricalWeather(args: unknown, noaaService: NOAAService, openMeteoService: OpenMeteoService): Promise<{
7
+ content: Array<{
8
+ type: string;
9
+ text: string;
10
+ }>;
11
+ }>;
12
+ //# sourceMappingURL=historicalWeatherHandler.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"historicalWeatherHandler.d.ts","sourceRoot":"","sources":["../../src/handlers/historicalWeatherHandler.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EAAE,WAAW,EAAE,MAAM,qBAAqB,CAAC;AAClD,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAK5D,wBAAsB,0BAA0B,CAC9C,IAAI,EAAE,OAAO,EACb,WAAW,EAAE,WAAW,EACxB,gBAAgB,EAAE,gBAAgB,GACjC,OAAO,CAAC;IAAE,OAAO,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,CAAC,CAAA;CAAE,CAAC,CA+N7D"}
@@ -0,0 +1,188 @@
1
+ /**
2
+ * Handler for get_historical_weather tool
3
+ */
4
+ import { validateHistoricalWeatherParams } from '../utils/validation.js';
5
+ import { convertToFahrenheit } from '../utils/temperatureConversion.js';
6
+ import { ApiConstants, FormatConstants } from '../config/displayThresholds.js';
7
+ export async function handleGetHistoricalWeather(args, noaaService, openMeteoService) {
8
+ // Validate input parameters with runtime checks
9
+ const { latitude, longitude, start_date, end_date, limit = FormatConstants.defaultHistoricalLimit } = validateHistoricalWeatherParams(args);
10
+ // Parse dates
11
+ const startTime = new Date(start_date);
12
+ const endTime = new Date(end_date);
13
+ // Validate dates are not in the future
14
+ const now = new Date();
15
+ if (startTime > now) {
16
+ throw new Error(`Start date (${start_date}) cannot be in the future. Current date is ${now.toISOString().split('T')[0]}.`);
17
+ }
18
+ if (endTime > now) {
19
+ throw new Error(`End date (${end_date}) cannot be in the future. Current date is ${now.toISOString().split('T')[0]}.`);
20
+ }
21
+ // Determine which API to use based on date range
22
+ // If start date is older than threshold, use archival API
23
+ const thresholdDate = new Date(now.getTime() - ApiConstants.historicalDataThresholdDays * 24 * 60 * 60 * 1000);
24
+ const useArchivalData = startTime < thresholdDate;
25
+ if (useArchivalData) {
26
+ // Use Open-Meteo API for historical/archival data
27
+ try {
28
+ // Determine whether to use hourly or daily data based on date range
29
+ const daysDiff = Math.ceil((endTime.getTime() - startTime.getTime()) / (1000 * 60 * 60 * 24));
30
+ const useHourly = daysDiff <= ApiConstants.maxHourlyHistoricalDays;
31
+ const weatherData = await openMeteoService.getHistoricalWeather(latitude, longitude, start_date.split('T')[0], // Ensure YYYY-MM-DD format
32
+ end_date.split('T')[0], useHourly);
33
+ // Format the response based on data granularity
34
+ if (useHourly && weatherData.hourly) {
35
+ // Format hourly observations
36
+ let output = `# Historical Weather Observations (Hourly)\n\n`;
37
+ output += `**Period:** ${startTime.toLocaleDateString()} to ${endTime.toLocaleDateString()}\n`;
38
+ output += `**Location:** ${weatherData.latitude.toFixed(4)}°N, ${Math.abs(weatherData.longitude).toFixed(4)}°${weatherData.longitude >= 0 ? 'E' : 'W'} (${weatherData.elevation}m elevation)\n`;
39
+ output += `**Number of observations:** ${weatherData.hourly.time.length}\n`;
40
+ output += `**Data source:** Open-Meteo Historical Weather API (Reanalysis)\n\n`;
41
+ const maxObservations = Math.min(limit, weatherData.hourly.time.length);
42
+ for (let i = 0; i < maxObservations; i++) {
43
+ const time = new Date(weatherData.hourly.time[i]);
44
+ output += `## ${time.toLocaleString()}\n`;
45
+ if (weatherData.hourly.temperature_2m?.[i] !== null && weatherData.hourly.temperature_2m?.[i] !== undefined) {
46
+ output += `- **Temperature:** ${Math.round(weatherData.hourly.temperature_2m[i])}°F\n`;
47
+ }
48
+ if (weatherData.hourly.apparent_temperature?.[i] !== null && weatherData.hourly.apparent_temperature?.[i] !== undefined) {
49
+ output += `- **Feels Like:** ${Math.round(weatherData.hourly.apparent_temperature[i])}°F\n`;
50
+ }
51
+ if (weatherData.hourly.weather_code?.[i] !== null && weatherData.hourly.weather_code?.[i] !== undefined) {
52
+ output += `- **Conditions:** ${openMeteoService.getWeatherDescription(weatherData.hourly.weather_code[i])}\n`;
53
+ }
54
+ if (weatherData.hourly.precipitation?.[i] !== null && weatherData.hourly.precipitation?.[i] !== undefined && weatherData.hourly.precipitation[i] > 0) {
55
+ output += `- **Precipitation:** ${weatherData.hourly.precipitation[i].toFixed(2)} in\n`;
56
+ }
57
+ if (weatherData.hourly.snowfall?.[i] !== null && weatherData.hourly.snowfall?.[i] !== undefined && weatherData.hourly.snowfall[i] > 0) {
58
+ output += `- **Snowfall:** ${weatherData.hourly.snowfall[i].toFixed(1)} in\n`;
59
+ }
60
+ if (weatherData.hourly.wind_speed_10m?.[i] !== null && weatherData.hourly.wind_speed_10m?.[i] !== undefined) {
61
+ output += `- **Wind:** ${Math.round(weatherData.hourly.wind_speed_10m[i])} mph`;
62
+ if (weatherData.hourly.wind_direction_10m?.[i] !== null && weatherData.hourly.wind_direction_10m?.[i] !== undefined) {
63
+ output += ` from ${Math.round(weatherData.hourly.wind_direction_10m[i])}°`;
64
+ }
65
+ output += `\n`;
66
+ }
67
+ if (weatherData.hourly.relative_humidity_2m?.[i] !== null && weatherData.hourly.relative_humidity_2m?.[i] !== undefined) {
68
+ output += `- **Humidity:** ${Math.round(weatherData.hourly.relative_humidity_2m[i])}%\n`;
69
+ }
70
+ if (weatherData.hourly.pressure_msl?.[i] !== null && weatherData.hourly.pressure_msl?.[i] !== undefined) {
71
+ const pressureInHg = weatherData.hourly.pressure_msl[i] * 0.02953;
72
+ output += `- **Pressure:** ${pressureInHg.toFixed(2)} inHg\n`;
73
+ }
74
+ if (weatherData.hourly.cloud_cover?.[i] !== null && weatherData.hourly.cloud_cover?.[i] !== undefined) {
75
+ output += `- **Cloud Cover:** ${weatherData.hourly.cloud_cover[i]}%\n`;
76
+ }
77
+ output += `\n`;
78
+ }
79
+ return {
80
+ content: [
81
+ {
82
+ type: 'text',
83
+ text: output
84
+ }
85
+ ]
86
+ };
87
+ }
88
+ else if (weatherData.daily) {
89
+ // Format daily summaries
90
+ let output = `# Historical Weather Data (Daily Summaries)\n\n`;
91
+ output += `**Period:** ${startTime.toLocaleDateString()} to ${endTime.toLocaleDateString()}\n`;
92
+ output += `**Location:** ${weatherData.latitude.toFixed(4)}°N, ${Math.abs(weatherData.longitude).toFixed(4)}°${weatherData.longitude >= 0 ? 'E' : 'W'} (${weatherData.elevation}m elevation)\n`;
93
+ output += `**Number of days:** ${weatherData.daily.time.length}\n`;
94
+ output += `**Data source:** Open-Meteo Historical Weather API (Reanalysis)\n\n`;
95
+ for (let i = 0; i < weatherData.daily.time.length; i++) {
96
+ const date = new Date(weatherData.daily.time[i]);
97
+ output += `## ${date.toLocaleDateString()}\n`;
98
+ if (weatherData.daily.temperature_2m_max?.[i] !== null && weatherData.daily.temperature_2m_max?.[i] !== undefined) {
99
+ output += `- **High Temperature:** ${Math.round(weatherData.daily.temperature_2m_max[i])}°F\n`;
100
+ }
101
+ if (weatherData.daily.temperature_2m_min?.[i] !== null && weatherData.daily.temperature_2m_min?.[i] !== undefined) {
102
+ output += `- **Low Temperature:** ${Math.round(weatherData.daily.temperature_2m_min[i])}°F\n`;
103
+ }
104
+ if (weatherData.daily.temperature_2m_mean?.[i] !== null && weatherData.daily.temperature_2m_mean?.[i] !== undefined) {
105
+ output += `- **Average Temperature:** ${Math.round(weatherData.daily.temperature_2m_mean[i])}°F\n`;
106
+ }
107
+ if (weatherData.daily.weather_code?.[i] !== null && weatherData.daily.weather_code?.[i] !== undefined) {
108
+ output += `- **Conditions:** ${openMeteoService.getWeatherDescription(weatherData.daily.weather_code[i])}\n`;
109
+ }
110
+ if (weatherData.daily.precipitation_sum?.[i] !== null && weatherData.daily.precipitation_sum?.[i] !== undefined) {
111
+ output += `- **Precipitation:** ${weatherData.daily.precipitation_sum[i].toFixed(2)} in\n`;
112
+ }
113
+ if (weatherData.daily.snowfall_sum?.[i] !== null && weatherData.daily.snowfall_sum?.[i] !== undefined && weatherData.daily.snowfall_sum[i] > 0) {
114
+ output += `- **Snowfall:** ${weatherData.daily.snowfall_sum[i].toFixed(1)} in\n`;
115
+ }
116
+ if (weatherData.daily.wind_speed_10m_max?.[i] !== null && weatherData.daily.wind_speed_10m_max?.[i] !== undefined) {
117
+ output += `- **Max Wind Speed:** ${Math.round(weatherData.daily.wind_speed_10m_max[i])} mph\n`;
118
+ }
119
+ output += `\n`;
120
+ }
121
+ return {
122
+ content: [
123
+ {
124
+ type: 'text',
125
+ text: output
126
+ }
127
+ ]
128
+ };
129
+ }
130
+ else {
131
+ throw new Error('No weather data available in response');
132
+ }
133
+ }
134
+ catch (error) {
135
+ // If Open-Meteo API fails, provide helpful error message
136
+ const errorMessage = error instanceof Error ? error.message : 'Unknown error';
137
+ throw new Error(`Unable to retrieve historical data: ${errorMessage}`);
138
+ }
139
+ }
140
+ else {
141
+ // Use real-time NOAA API for recent data (last 7 days)
142
+ const observations = await noaaService.getHistoricalObservations(latitude, longitude, startTime, endTime, limit);
143
+ if (!observations.features || observations.features.length === 0) {
144
+ return {
145
+ content: [
146
+ {
147
+ type: 'text',
148
+ text: `No historical observations found for the specified date range (${start_date} to ${end_date}).\n\nThis may occur because:\n- The dates are outside the station's available data range\n- There are gaps in the observation records for this location\n- The weather station near this location may not have archived data for these dates\n\nNote: Historical weather data availability varies by location and weather station. Some stations have limited historical records.`
149
+ }
150
+ ]
151
+ };
152
+ }
153
+ // Format the observations
154
+ let output = `# Historical Weather Observations\n\n`;
155
+ output += `**Period:** ${startTime.toLocaleDateString()} to ${endTime.toLocaleDateString()}\n`;
156
+ output += `**Number of observations:** ${observations.features.length}\n`;
157
+ output += `**Data source:** NOAA Real-time API\n\n`;
158
+ for (const obs of observations.features) {
159
+ const props = obs.properties;
160
+ output += `## ${new Date(props.timestamp).toLocaleString()}\n`;
161
+ if (props.temperature.value !== null) {
162
+ const tempF = convertToFahrenheit(props.temperature.value, props.temperature.unitCode);
163
+ if (tempF !== null) {
164
+ output += `- **Temperature:** ${Math.round(tempF)}°F\n`;
165
+ }
166
+ }
167
+ if (props.textDescription) {
168
+ output += `- **Conditions:** ${props.textDescription}\n`;
169
+ }
170
+ if (props.windSpeed.value !== null) {
171
+ const windMph = props.windSpeed.unitCode.includes('km_h')
172
+ ? props.windSpeed.value * 0.621371
173
+ : props.windSpeed.value * 2.23694;
174
+ output += `- **Wind:** ${Math.round(windMph)} mph\n`;
175
+ }
176
+ output += `\n`;
177
+ }
178
+ return {
179
+ content: [
180
+ {
181
+ type: 'text',
182
+ text: output
183
+ }
184
+ ]
185
+ };
186
+ }
187
+ }
188
+ //# sourceMappingURL=historicalWeatherHandler.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"historicalWeatherHandler.js","sourceRoot":"","sources":["../../src/handlers/historicalWeatherHandler.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,11 @@
1
+ /**
2
+ * Handler for search_location tool
3
+ */
4
+ import { OpenMeteoService } from '../services/openmeteo.js';
5
+ export declare function handleSearchLocation(args: unknown, openMeteoService: OpenMeteoService): Promise<{
6
+ content: Array<{
7
+ type: string;
8
+ text: string;
9
+ }>;
10
+ }>;
11
+ //# sourceMappingURL=locationHandler.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"locationHandler.d.ts","sourceRoot":"","sources":["../../src/handlers/locationHandler.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAQ5D,wBAAsB,oBAAoB,CACxC,IAAI,EAAE,OAAO,EACb,gBAAgB,EAAE,gBAAgB,GACjC,OAAO,CAAC;IAAE,OAAO,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,CAAC,CAAA;CAAE,CAAC,CA0F7D"}