Entree: Weather API Server
An MCP server that fetches real weather data from Open-Meteo. Learn to integrate external APIs, handle errors, and return structured data to AI assistants.
title: "Entree: Weather API Server" description: "An MCP server that fetches real weather data from Open-Meteo. Learn to integrate external APIs, handle errors, and return structured data to AI assistants." order: 3 category: "entree" level: "intermediate" duration: "20 min" date: "2026-04-01" tags:
- tools
- api
- weather keywords:
- mcp weather server
- mcp-framework api integration
- weather api mcp
- open-meteo mcp
What You Get
A production-quality MCP server that lets Claude check the weather for any city. It uses the free Open-Meteo API — no API key required.
Tools included:
get_weather— fetch current weather for a city (temperature, humidity, wind speed, conditions)get_forecast— get a multi-day weather forecast
Quick Start
npx mcp-framework create weather-server
cd weather-server
The Weather Tool
Create src/tools/GetWeatherTool.ts:
import { MCPTool } from "mcp-framework";
import { z } from "zod";
const WeatherInput = z.object({
city: z.string().describe("City name (e.g. 'London', 'New York')"),
});
class GetWeatherTool extends MCPTool<typeof WeatherInput> {
name = "get_weather";
description = "Get current weather for a city using Open-Meteo";
schema = { input: WeatherInput };
async execute(input: z.infer<typeof WeatherInput>) {
// Step 1: Geocode the city
const geoRes = await fetch(
`https://geocoding-api.open-meteo.com/v1/search?name=${encodeURIComponent(input.city)}&count=1`
);
const geoData = await geoRes.json();
if (!geoData.results?.length) {
throw new Error(`City not found: ${input.city}`);
}
const { latitude, longitude, name, country } = geoData.results[0];
// Step 2: Fetch weather
const weatherRes = await fetch(
`https://api.open-meteo.com/v1/forecast?latitude=${latitude}&longitude=${longitude}¤t=temperature_2m,relative_humidity_2m,wind_speed_10m,weather_code`
);
const weatherData = await weatherRes.json();
const current = weatherData.current;
return {
location: `${name}, ${country}`,
temperature: `${current.temperature_2m}°C`,
humidity: `${current.relative_humidity_2m}%`,
windSpeed: `${current.wind_speed_10m} km/h`,
conditionCode: current.weather_code,
};
}
}
export default GetWeatherTool;
The Forecast Tool
Create src/tools/GetForecastTool.ts:
import { MCPTool } from "mcp-framework";
import { z } from "zod";
const ForecastInput = z.object({
city: z.string().describe("City name"),
days: z.number().min(1).max(7).default(3).describe("Number of forecast days"),
});
class GetForecastTool extends MCPTool<typeof ForecastInput> {
name = "get_forecast";
description = "Get a multi-day weather forecast";
schema = { input: ForecastInput };
async execute(input: z.infer<typeof ForecastInput>) {
const geoRes = await fetch(
`https://geocoding-api.open-meteo.com/v1/search?name=${encodeURIComponent(input.city)}&count=1`
);
const geoData = await geoRes.json();
if (!geoData.results?.length) {
throw new Error(`City not found: ${input.city}`);
}
const { latitude, longitude, name, country } = geoData.results[0];
const weatherRes = await fetch(
`https://api.open-meteo.com/v1/forecast?latitude=${latitude}&longitude=${longitude}&daily=temperature_2m_max,temperature_2m_min,weather_code&forecast_days=${input.days}`
);
const data = await weatherRes.json();
return {
location: `${name}, ${country}`,
forecast: data.daily.time.map((date: string, i: number) => ({
date,
high: `${data.daily.temperature_2m_max[i]}°C`,
low: `${data.daily.temperature_2m_min[i]}°C`,
conditionCode: data.daily.weather_code[i],
})),
};
}
}
export default GetForecastTool;
Error Handling
Notice how both tools throw descriptive errors when a city is not found. mcp-framework will automatically catch these and return them as structured error responses to the AI assistant.
Build & Connect
npm run build
{
"mcpServers": {
"weather": {
"command": "node",
"args": ["./dist/index.js"]
}
}
}
What You Learn
- Integrating external REST APIs in MCP tools
- Chaining API calls (geocoding then weather)
- Returning structured data that AI can reason about
- Input validation with defaults (
daysdefaults to 3) - Error handling patterns for MCP servers
Next Up
Try the Database Query Server or the GitHub Integration Server for more real-world patterns.
Built with mcp-framework (3.3M+ downloads) by @QuantGeekDev. Validated by Anthropic.