solar_mcp
solar-plan-mcp
Ein Agent, der eine alltägliche Frage beantwortet: schaffe ich morgen diesen Satz Verbraucher mit meiner eigenen Erzeugung, und wenn nicht – was verschiebe ich?
Dach mit Modulen, Batterie, Wechselrichter, bekannter Abschaltplan. Der Agent holt die Wettervorhersage von einem fertigen MCP-Server, berechnet die erwartete Erzeugung stundenweise auf einem eigenen MCP-Server, prüft den Plan gegen physikalische Regeln, und wenn er nicht durchgeht – verschiebt er flexible Lasten und belegt mit Zahlen, dass es besser geworden ist.
Zwei MCP-Verbindungen:
Server | Rolle | |
Fertig |
| Vorhersage: Himmelsklasse und Temperatur alle 3 Stunden |
Eigen |
| 4 inhaltliche Domänen-Tools + Textanalyse der Vorhersage |
Dokumentation: Tool-Verträge · Design-Begründung · Demonstrationsszenario
Was benötigt wird
Wofür | Hinweis | |
Python 3.13 | Agent und eigener Server | keine Administratorrechte nötig |
Go 1.24+ | nur um den Wetterserver zu bauen | das Projekt veröffentlicht keine fertigen Binaries; |
OpenWeather-Schlüssel | Wetterserver | kostenlos, openweathermap.org/api; aktiviert sich erst nach bis zu einigen Stunden |
| nur Agent; eigener Server und Tests brauchen ihn nicht | Das Claude Agent SDK startet diese CLI als Kindprozess – siehe Modellzugang |
Node + npx | optional – MCP Inspector |
|
Der PVGIS-Datensatz liegt bereits im Repository (data/pvgis_kyiv_5kwp.csv, 1,1 MB), daher
arbeitet der eigene Server ohne Netzwerk. Es muss nichts heruntergeladen werden.
Related MCP server: KinSwitch
Installation
Windows, und das ist keine Kosmetik: alle Befehle laufen in PowerShell, denn && ist in
PowerShell 5.1 überhaupt kein Operator. Im Folgenden überall .venv\Scripts\python.exe.
Zuerst zwei Codierungsvariablen, und sie sind verschieden. PYTHONUTF8=1 sagt Python,
UTF-8 zu schreiben; [Console]::OutputEncoding sagt PowerShell, es ebenso zu lesen.
Ohne die zweite wird die ukrainische Ausgabe zu ╨▓╨╗╨░╤ü╨╜╨╕╨╣ – gemessen, und genau in der
Pipe (| Tee-Object, | Select-String), denn dort dekodiert PowerShell die Bytes mit der
Codepage der Konsole. In jedem neuen Fenster setzen, und vor der Installation, nicht danach:
[Console]::OutputEncoding = [Text.Encoding]::UTF8
$env:PYTHONUTF8 = "1"git clone https://github.com/prasolantoncp-bot/solar-plan-mcp.git
cd solar-plan-mcp
python -m venv .venv # або: uv venv .venv
.venv\Scripts\python.exe -m pip install -r requirements.txtBenötigt wird Python 3.13 – genau das, das auf python --version antwortet, denn venv
erbt die Version des Interpreters, mit dem es erstellt wurde.
Warum die Versionen gepinnt sind. Die Demonstration soll reproduzierbar sein, nicht
„irgendwo funktionieren“. mcp==2.0.0 ist bereits MCPServer statt FastMCP, und der Code
für 1.x funktioniert hier nicht; claude-agent-sdk==0.2.144 – darauf sind tools und das
Format der Init-Nachricht geprüft, aus dem der Agent beide Verbindungen ausgibt; tzdata –
denn Windows hat keine systemweite Zeitzonen-Datenbank, und ohne Europe/Kyiv gibt es keine
einzige lokale Stunde. Die requirements.txt selbst ist absichtlich in ASCII gehalten: pip
liest sie mit der Locale-Codierung, und ein einziges kyrillisches Zeichen in einem Kommentar
lässt pip install -r mit UnicodeDecodeError auf jeder Maschine scheitern, deren Locale
nicht UTF-8 ist. Gemessen auf cp1252 aus einem frischen Klon – deshalb lebt die Erklärung hier
und nicht in jener Datei.
Wetterserver bauen
Go wird im Benutzerprofil installiert, ohne Administrator und ohne Änderungen an der Registry:
# 1. портативний Go у профіль (один раз). curl.exe є у Windows 10 1803+
curl.exe -Lo go.zip https://go.dev/dl/go1.27.0.windows-amd64.zip
Expand-Archive go.zip -DestinationPath "$env:LOCALAPPDATA\Programs"
# 2. клон і збірка. GOROOT і PATH живуть лише в цьому вікні — так і треба
$env:GOROOT = "$env:LOCALAPPDATA\Programs\go"
$env:PATH = "$env:GOROOT\bin;$env:PATH"
New-Item -ItemType Directory -Force vendor | Out-Null
cd vendor
git clone https://github.com/mschneider82/mcp-openweather.git
cd mcp-openweather
git checkout e032683574a0723591445462ef7104d360ad0889
go build -o mcp-weather.exe .
cd ..\..Das fertige Binary sucht der Agent unter
vendor\mcp-openweather\mcp-weather.exe. Liegt es bei dir anders – nicht verschieben, sondern
eine Variable setzen: $env:WEATHER_MCP_BINARY = "…\mcp-weather.exe" (siehe
env.example). Der Agent prüft die Existenz der Datei vor dem Start der
Sitzung und lehnt mit einem Satz ab, nicht mit einem Traceback aus dem SDK.
vendor/ in .gitignore: fremde Git-Historie und 13 MB Binary haben in diesem Repository
nichts zu suchen. Der Commit ist fixiert – auf genau ihm basiert die
Vertragsdokumentation.
Wenn der Kurs einen anderen Commit von
mcp-openweatherfixiert – nimm ihn und notiere ihn hier; die Vertragsbeschreibung indocs/TOOLS.mdwurde mitmain.goaufe032683geschrieben.
Schlüssel
Geheimnisse gelangen nicht ins Repository: .env und .env.* stehen in .gitignore, und die
Vorlage liegt in env.example ohne jeden Wert.
Die Demonstration braucht drei Terminals, und $env: lebt nur in einem, daher lohnt es sich,
den Schlüssel auf Benutzerebene zu setzen – Administratorrechte sind dafür nicht nötig:
# так ключ не потрапляє ні в скролбек, ні в історію PSReadLine
$s = Read-Host "OWM_API_KEY" -AsSecureString
[Environment]::SetEnvironmentVariable("OWM_API_KEY",
[Runtime.InteropServices.Marshal]::PtrToStringBSTR(
[Runtime.InteropServices.Marshal]::SecureStringToBSTR($s)), "User")Den neuen Wert sehen nur neue Terminals. Prüfung, dass er angekommen ist, ohne den Schlüssel
preiszugeben: .venv/Scripts/python.exe -c "import os; print(len(os.environ.get('OWM_API_KEY','')))"
– muss 32 ergeben. Vor der Kamera kein dir env: ausführen: das druckt den Schlüssel.
Die einmalige Sitzungsform $env:OWM_API_KEY = "…" funktioniert ebenfalls, hat hier aber genau
eine richtige Anwendung – den Schlüssel in einem separaten Fenster für das Fehlerszenario
zurückzusetzen: $env:OWM_API_KEY = "".
Der Schlüssel wird nur aus der Umgebung gelesen – weder im Code noch in
.mcp.json.example gibt es ihn; dort steht die Substitution ${OWM_API_KEY}. Die Datei .env
liest niemand: im Code steht nur os.environ.get, daher ist das Kopieren von env.example
nach .env eine leere Handlung.
Zugang zum Modell
Der eigene Server und alle 57 Tests funktionieren ohne jegliche Anthropic-Zugangsdaten –
das sind verschiedene Dinge und sollte man nicht verwechseln. Das Modell braucht genau eine
Datei, agent/run.py.
Das Claude Agent SDK spricht die API nicht selbst an: Es startet die claude CLI als
Kindprozess, und genau diese CLI sucht die Autorisierung. Daher werden zwei Dinge benötigt:
claudeimPATH. Prüfung:(Get-Command claude).Source. Installation – nach der offiziellen Anleitung; in diesem Projekt wurde es über WinGet installiert und liegt unter%LOCALAPPDATA%\Microsoft\WinGet\Links\claude.exe.Autorisierung – einer von zwei Wegen, und die CLI nimmt den, den sie findet:
claude login– interaktive Anmeldung; das Token legt die CLI in~/.claude/.credentials.json. Genau dieser Weg wurde hier verwendet: In der Prozessumgebung gibt es keine einzige VariableANTHROPIC_*, die Zugangsdatendatei existiert aber. Der aufgezeichnete Lauf vom 25. August 2026 lief so.ANTHROPIC_API_KEYin der Umgebung – Schlüssel von console.anthropic.com. Wird genauso gesetzt wieOWM_API_KEYoben und gelangt ebenso wenig ins Repository.
Was im Code gepinnt ist: das Modell claude-opus-5 (agent/run.py) und
claude-agent-sdk==0.2.144 (requirements.txt). Wenn du anderen Zugang
hast und diese Modell-ID nicht aufgelöst wird – ersetze sie in run.py durch eine verfügbare
und notiere hier, welche genau; der Rest des Laufs hängt nicht von der ID ab.
Keine einzige Zugangsdatei liest oder übergibt dieser Code: agent/run.py greift weder auf
ANTHROPIC_API_KEY noch auf die Zugangsdatendatei zu – das erledigt die CLI. Im Repository
gibt es keine Geheimnisse, und env.example liegt leer.
Limits der externen API
Der kostenlose OpenWeather-Plan erlaubt 60 Aufrufe pro Minute
(Dokumentation). Ein Agentenlauf macht einen
Aufruf des Tools weather; im Inneren verwandelt der Wetterserver ihn in zwei HTTP-Anfragen
(aktuelles Wetter + 5-Tage-Vorhersage). Das heißt, bis zur Obergrenze bleiben drei
Größenordnungen Reserve, selbst bei ununterbrochenen Proben.
Im Code gibt es keine Abfrageschleife, keinen Wiederholungsversuch bei Fehlern und kein
Hintergrund-Update: Das Wetter wird genau dann abgefragt, wenn das Modell das Tool aufruft.
Der eigene Server geht überhaupt nicht ins Netz – sein Datensatz liegt in data/, daher
erzeugen beliebig viele Läufe von estimate_pv_generation, validate_energy_plan und dem
Rest keine einzige externe Anfrage.
Start: zwei unabhängige Prozesse
Der eigene Server wird getrennt vom Agenten gestartet und weiß nichts über den Agenten.
Terminal 1 – eigener MCP-Server:
$env:PYTHONUTF8 = "1"
.venv\Scripts\python.exe -m solar_mcp --transport streamable-http --port 8931Terminal 2 – Agent:
[Console]::OutputEncoding = [Text.Encoding]::UTF8
$env:PYTHONUTF8 = "1"
.venv\Scripts\python.exe agent\run.pyOhne --date plant der Agent den morgigen Tag: Die Produktfrage betrifft genau morgen,
und die OpenWeather-Vorhersage deckt nur jetzt … +5 Tage ab, daher liegt der heutige Tag
schon zur Hälfte außerhalb des Horizonts. Ein Datum außerhalb dieses Fensters ergibt
NO_FORECAST_FOR_DATE, nicht stille Nullen.
Den Wetterserver startet der Agent selbst, über stdio – so ist die Verbindung konfiguriert.
Den eigenen Server kann man ebenfalls über stdio starten (python -m solar_mcp, das ist der
Standard) – so erwarten ihn Clients wie Claude Code, und genau diese Variante ist in
.mcp.json.example beschrieben. Für die Demonstration ist HTTP besser:
Dann sieht man, dass der Server wirklich ein eigener Prozess ist.
Nützliche Agenten-Flags:
--plan boiler:18:2 --plan aircon:18:3 # свій план замість дефолтного (можна кілька разів)
--date YYYY-MM-DD # інша доба; вт/чт/пт — без відключень, сб/нд — вечірнє вікно
--objective maximize_outage_reserve # інша цільова функція
--city Lviv # інше місто
--width 120 # скільки символів сліду друкувати--date akzeptiert nur einen Tag innerhalb des Vorhersagehorizonts – morgen … heute + 5.
Ein Datum außerhalb ergibt NO_FORECAST_FOR_DATE, und das Vorhandensein eines
Abschaltfensters im Plan rettet das nicht: Der Plan liegt im Repository und kennt jedes Datum,
die Vorhersage lebt fünf Tage. Vor dem Start prüfen: scripts/call_weather.py --city Kyiv --covers YYYY-MM-DD.
Die Daten im Abschaltplan haben ein wöchentliches Muster und eine Herkunft – siehe
data/outage_windows.json: Die Fenster für den 22.–26. August
stammen aus dem öffentlichen Zeitplan, danach wird dasselbe Muster nach vorne wiederholt,
damit die Demonstration nicht vom Aufnahmedatum abhängt.
Prüfung, dass alles lebt
# 4 інструменти домену + 1 допоміжний, зі схемами входу І виходу
.venv\Scripts\python.exe scripts\inspect_tools.py
.venv\Scripts\python.exe scripts\inspect_tools.py --url http://127.0.0.1:8931/mcp --schemas
# сервер погоди напряму: сирий текст і те, що з нього вийшло
.venv\Scripts\python.exe scripts\call_weather.py --city Kyiv
# 57 тестів: фізика, правила домену, планувальник, контракт через MCP-клієнта
$env:PYTHONUTF8 = "1"; $env:PYTHONPATH = "."
.venv\Scripts\python.exe -m pytest tests\ -qDie Tests brauchen weder Netzwerk noch OpenWeather-Schlüssel noch Modellzugang: Der Datensatz
liegt im Repository, und die Antworten des fremden Servers sind in
tests/fixtures/ aufgezeichnet.
Was wo liegt
solar_mcp/ власний MCP-сервер (окремий процес)
server.py інструменти й ресурс — увесь контракт
models.py схеми входу й виходу (Pydantic → справжні inputSchema/outputSchema)
errors.py закритий перелік кодів; помилка ≠ порожній результат
pv.py огинаюча ясного неба × прозорість × температурний дерейтинг
rules.py симуляція балансу, порушення, планувальник, порівняння
forecast.py розбір плоского тексту сервера погоди
dataset.py store.py читання датасету; реєстр виданих оцінок
agent/run.py Claude Agent SDK, дві MCP-конекції, слід викликів
scripts/ inspect_tools.py — контракт; call_weather.py — чужий сервер напряму
data/ датасет + fetch_pvgis.py (провенанс)
tests/ 57 тестів; у fixtures/ — три записані відповіді сервера погоди й одна синтетична
docs/ TOOLS.md · DESIGN.md · DEMO.mdZwei dieser Verzeichnisse haben ein eigenes README, und genau sie sucht man unter
„Datenquelle“ und „Fixtures“: data/README.md – woher die PVGIS-Zeile, der
Tarif und der Abschaltplan stammen; tests/fixtures/README.md –
was genau vom fremden Server aufgezeichnet wurde, wann und womit.
Eine Beobachtung, auf der die Hälfte des Designs steht
Der Wetterserver unterscheidet einen Defekt nicht von einer leeren Antwort. Ohne Schlüssel
gibt er is_error: false und einen Text mit Nullen und leerem Stadtnamen zurück – wörtlich
aufgezeichnet in tests/fixtures/owm_no_api_key.txt,
obwohl sein README „FATAL: OWM_API_KEY environment variable not set“ verspricht.
Deshalb ist der eigene Server umgekehrt gebaut: eine geschlossene Liste von Fehlercodes,
field mit Verweis auf das schuldige Feld, und separat – reason dort, wo Leere legitim ist
(Nacht, keine Verstöße). Details: DESIGN.md, TOOLS.md.
This server cannot be deployed
Maintenance
Related MCP Connectors
Home energy for AI assistants: live Power flow, Energy history, solar forecast, and device control.
Solar, weatherization, EV charging, battery and heat-pump decision tools for AI agents.
EU power dispatch for wallet-enabled compute, DePIN, battery and trading agents.
Solar power estimates from the electricity bill, and the service area check, for São Paulo, Brazil.
Related MCP Servers
- FlicenseNot gradedqualityDmaintenanceEnables AI-powered analysis and prediction of household energy consumption through machine learning models, providing historical consumption breakdowns, price queries from Spanish electricity markets, and personalized energy optimization recommendations.-
- AlicenseNot gradedqualityBmaintenanceEnables AI agents to manage household schedules by checking availability, proposing minimal changes, and requiring explicit human approval before executing any action.MIT
- AlicenseNot gradedqualityBmaintenanceEnables conversational home power management by providing real-time solar, battery, and grid status, plus forecasts to answer questions like whether you can run an appliance. It supports Victron and Growatt inverters, remembers household appliances and grid events, and renders an interactive dashboard card in MCP-compatible clients.5 npmMIT
- AlicenseNot gradedqualityAmaintenanceEnables AI assistants to size hybrid renewable energy systems by simulating candidate designs hour-by-hour for a full year, filtering out constraint violations, and ranking remaining options by net present cost and related techno-economic metrics.Apache 2.0