using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Text.Json; using System.Net.Http; using System.Net.Http.Json; using System.Globalization; namespace McpStudy.Core; [McpServerToolType] public sealed class WeatherTools { [McpServerTool, Description("Get weather alerts for a US state.")] public static async Task GetAlerts( HttpClient client, [Description("The US state to get alerts for. Use the 2 letter abbreviation for the state (e.g. NY).")] string state) { using var jsonDocument = await ReadJsonDocumentAsync(client,$"/alerts/active/area/{state}"); var jsonElement = jsonDocument.RootElement; var alerts = jsonElement.GetProperty("features").EnumerateArray(); if (!alerts.Any()) { return "No active alerts for this state."; } return string.Join("\n--\n", alerts.Select(alert => { JsonElement properties = alert.GetProperty("properties"); return $""" Event: {properties.GetProperty("event").GetString()} Area: {properties.GetProperty("areaDesc").GetString()} Severity: {properties.GetProperty("severity").GetString()} Description: {properties.GetProperty("description").GetString()} Instruction: {properties.GetProperty("instruction").GetString()} """; })); } [McpServerTool, Description("Get weather forecast for a location.")] public static async Task GetForecast( HttpClient client, [Description("Latitude of the location.")] double latitude, [Description("Longitude of the location.")] double longitude) { var pointUrl = string.Create(CultureInfo.InvariantCulture, $"/points/{latitude},{longitude}"); using var jsonDocument = await ReadJsonDocumentAsync(client,pointUrl); var forecastUrl = jsonDocument.RootElement.GetProperty("properties").GetProperty("forecast").GetString() ?? throw new Exception($"No forecast URL provided by {client.BaseAddress}points/{latitude},{longitude}"); using var forecastDocument = await ReadJsonDocumentAsync(client,forecastUrl); var periods = forecastDocument.RootElement.GetProperty("properties").GetProperty("periods").EnumerateArray(); return string.Join("\n---\n", periods.Select(period => $""" {period.GetProperty("name").GetString()} Temperature: {period.GetProperty("temperature").GetInt32()}°F Wind: {period.GetProperty("windSpeed").GetString()} {period.GetProperty("windDirection").GetString()} Forecast: {period.GetProperty("detailedForecast").GetString()} """)); } public static async Task ReadJsonDocumentAsync(HttpClient client, string requestUri) { using var response = await client.GetAsync(requestUri); response.EnsureSuccessStatusCode(); return await JsonDocument.ParseAsync(await response.Content.ReadAsStreamAsync()); } }