pvnodepvnode
  • pvnode.com
  • Studio
  • Pricing
  • Deutsch
  • English
  • API Reference
Product
  • Studio
  • API Documentation
  • API Reference
  • Pricing
Resources
  • Quickstart
  • Integrations
Legal
  • Imprint
  • Privacy
  • Terms
  • Licenses
pvnodepvnode

© 2026 pvnode. All rights reserved.

linkedin
EinführungSchnellstartMigration von V1
Standorte & Daten
    Standorte & SolarflächenPrognosenHistorische DatenDaten-UploadKalibrierung & Monitoring
Guides
Enterprise
Integrationen
    Eigene Integration bauenHome AssistantevccSolectrusioBroker
Datenquellen
(Archiv) V1 API
powered by Zudoku
Standorte & Daten

Prognosen

Die Prognose liefert die erwartete PV-Leistung für einen Standort in 15-Minuten-Intervallen. Sie fragen sie über die site_id ab; Standort, Strings und Konfiguration kommen aus dem gespeicherten Standort.

TerminalCode
GET /v2/forecast/{site_id}

Zeitstempel sind standardmäßig in der lokalen Zeitzone des Standorts (siehe timezone in der Antwort). Mit ?timezone=utc erhalten Sie stattdessen UTC-Zeitstempel mit Z am Ende.

Die vollständige Parameter- und Feldliste steht in der API-Referenz. Diese Seite erklärt die Konzepte.

Parameter

ParameterBedeutung
forecast_daysPrognosehorizont in Tagen. Ohne Angabe das Plan-Maximum. Hartes Limit 7, zusätzlich auf das Plan-Limit gekappt.
past_daysVergangene Tage vor heute (archivierte Prognose). Standard 0. Hartes Limit 30, auf das Plan-Limit gekappt.
includeWelche Feldgruppen zurückkommen (wiederholbar). Standard default.
timezoneZeitzone der Zeitstempel: local (Standard) oder utc. utc liefert UTC-Zeitstempel mit Z am Ende.

past_days liefert archivierte Prognosedaten, nicht echte Messwerte. Für tatsächliche vergangene Erträge nutzen Sie die Historischen Daten.

include-Gruppen

include ist wiederholbar und wählt Feldgruppen — nicht einzelne Spalten:

TerminalCode
GET /v2/forecast/{site_id}?include=weather&include=irradiance
GruppeFelder
defaultpv_power (PV-Leistung in W).
weathertemp, weather_code, wind_speed, relative_humidity, precipitation_mm, snow_water_equivalent.
irradianceghi, dhi, bni (horizontale Einstrahlung).
clearskypv_power_clearsky (Leistung bei wolkenlosem Himmel).
stringsFügt den separaten strings-Block hinzu (siehe unten). values bleibt unverändert.
variabilityFügt das Min/Max-Band hinzu (siehe unten). Kostenpflichtig, nie Teil von all.
allAlle Feldgruppen und den strings-Block (aber nicht variability).

default wird nicht automatisch ergänzt. Fragen Sie nur weather an, erhalten Sie Wetterdaten ohne pv_power. Das Feld included in der Antwort spiegelt die aufgelöste Auswahl.

Was Ihr Plan erlaubt (available)

included spiegelt wider, was Sie angefragt haben. available listet jede Gruppe, die Ihr Plan auf diesem Endpunkt anfragen darf:

Code
"included": ["default", "strings"], "available": ["default", "weather", "irradiance", "clearsky", "strings", "variability" ]

Damit erkennt ein Client seine Berechtigungen, ohne Plan-Wissen fest einzucodieren. Ein Dashboard kann eine Funktion ausgrauen, die der Plan nicht abdeckt, und sie nach einem Upgrade von selbst freischalten.

  • Plan-gebundene Gruppen erscheinen erst, wenn der Plan sie enthält.
  • Das Meta-Token all steht nicht in der Liste: Es ist die Kurzform für alle Gruppen hier außer variability, das immer explizit angefragt werden muss.
  • available gibt den Plan im Moment der Antwort wieder. Ein Planwechsel ist also mit der nächsten Anfrage sichtbar, nicht rückwirkend in der, die Sie schon halten.

Antwortstruktur

Code
{ "site_id": "site_rv8wm5…", "timezone": "Europe/Berlin", "computed_at": "2026-06-09T08:00:00", "next_poll_at": "2026-06-09T12:00:00", "included": [ "default" ], "available": [ "default", "weather", "irradiance", "clearsky", "strings" ], "daily": [ { "date": "2026-06-09", "pv_energy_kwh": 42.7, "temp_min": 11.0, "temp_max": 24.3 } ], "values": [ { "timestamp": "2026-06-09T12:00:00", "pv_power": 8200.0 } ] }
  • daily — Tagesaggregate (Energie in kWh, Min/Max-Temperatur, dominanter Wettercode).
  • values — Zeitreihe je 15 Minuten. pv_power ist die Summe über alle Strings.
  • computed_at — wann diese Prognose berechnet wurde (siehe Caching).
  • next_poll_at — wann sich eine erneute Abfrage lohnt. Nur auf /v2/forecast/{site_id}.
  • included / available — was Sie bekommen haben und was Ihr Plan erlaubt (siehe oben).

Der strings-Block

Mit include=strings (oder all) kommt ein separates Top-Level-Array strings im Long-/Tidy-Format hinzu — eine Zeile pro Zeitschritt und String:

Code
"strings": [ {"timestamp": "2026-06-09T12:00:00", "string_index": 0, "string_id": "str_9f3a1c08", "pv_power": 5100.0, "gti": 820.0, "gti_shaded": 815.0}, {"timestamp": "2026-06-09T12:00:00", "string_index": 1, "string_id": "str_4b7e2d10", "pv_power": 3100.0, "gti": 760.0, "gti_shaded": 752.0} ]
  • string_index verweist positionsbasiert auf site.strings[i] — gleiche Reihenfolge wie in GET /v2/sites/{site_id}. Immer vorhanden.
  • string_id ist die stabile ID des Strings — der Verknüpfungsschlüssel zu seinen Messwerten. Bei gespeicherten Sites vorhanden; beim Inline-Endpunkt nur, wenn Sie am String eine id mitgegeben haben.
  • Die geneigte Einstrahlung (gti, gti_shaded) liegt hier, nicht in values, weil sie von der String-Ausrichtung abhängt.
  • Jeder String liefert in jedem Zeitschritt eine Zeile (nachts 0.0), daher keine Lücken.
  • values.pv_power ist die Summe der String-Leistungen.

In einem DataFrame lässt sich der Block direkt laden und auf string_index pivotieren:

Code
import pandas as pd df = pd.DataFrame(response["strings"]) wide = df.pivot(index="timestamp", columns="string_index", values="pv_power")

Variabilitätsband (include=variability)

Das Band liefert eine Unter-/Obergrenze der PV-Leistung, sofern in Ihrem Plan verfügbar. Eine Anfrage mit include=variability auf einem Plan ohne diese Funktion gibt 403 zurück.

  • Felder: pv_power_min / pv_power_max in jeder values- und strings-Zeile sowie pv_energy_kwh_min / pv_energy_kwh_max in daily.
  • Horizont: deckt etwa die nächsten 48 h ab. Außerhalb (und für past_days) gilt min == max == pv_power (flaches Band). Nicht abgedeckte Standorte erhalten ebenfalls ein flaches Band — keinen Fehler.
  • variability wird nie von all mit eingeschlossen, sondern nur auf expliziten Wunsch.

Caching, computed_at und next_poll_at

Prognosen werden nicht bei jeder Anfrage neu berechnet, sondern nur so oft, wie Ihr Plan es zulässt. Wiederholte Anfragen im selben Slot liefern dasselbe zwischengespeicherte Ergebnis; computed_at zeigt den Berechnungszeitpunkt.

Der Cache wird automatisch ungültig, wenn sich der Standort ändert (Koordinaten, Strings, Config) oder der Plan wechselt.

Wann sich eine erneute Abfrage lohnt

next_poll_at nennt den frühesten Zeitpunkt, zu dem eine Anfrage eine neue Prognose liefert. Wer früher eine neue Prognose abfragt, verbraucht eine Anfrage und bekommt exakt dieselbe zwischengespeicherte Antwort zurück.

Code
"computed_at": "2026-06-09T08:00:00", "next_poll_at": "2026-06-09T12:00:00"

Es wird nichts nach Zeitplan neu berechnet — Prognosen entstehen auf Anfrage. Heute verteilen sich die Update-Slots gleichmäßig über den Tag, beginnend um Mitternacht Ortszeit des Standorts:

Updates pro TagSlots
1die nächste lokale Mitternacht
400:00 / 06:00 / 12:00 / 18:00
96alle 15 Minuten

Pläne mit mehr als 96 Updates pro Tag werden auf dem 15-Minuten-Raster ausgewiesen; next_poll_at liegt damit nie näher als 15 Minuten in der Zukunft.

Lesen Sie das Feld — bilden Sie die Regel nicht nach. Die gleichmäßige Verteilung oben beschreibt, wie die Slots heute liegen, und das wird sich ändern: Wir wollen nachts, wenn nichts erzeugt wird, weniger davon vergeben und dafür mehr in den Stunden, auf die es ankommt. Ein Client, der sich seinen nächsten Slot aus dem Plan selbst ausrechnet, fragt dann zu den falschen Zeiten ab. Einer, der next_poll_at liest, geht die Änderung automatisch mit.

Verstehen Sie den Wert als Empfehlung, nicht als Zusage. Eine durch eine andere Anfrage ausgelöste Neuberechnung kann neuere Daten früher verfügbar machen. Auf next_poll_at zu pollen ist die günstigste korrekte Strategie.

Für next_poll_at gelten dieselben Zeitzonenregeln wie für computed_at (standardmäßig Ortszeit mit UTC-Offset, mit ?timezone=utc endend auf …Z). Auf /forecast/inline fehlt das Feld, weil dort jede Anfrage frisch berechnet wird.

Header zum Anfragekontingent

Jede Antwort — auch die 429 — trägt vier Header, die Ihr Monatskontingent beschreiben:

HeaderBedeutung
RequestLimit-LimitErlaubte Anfragen in diesem Kalendermonat, oder wörtlich unmetered.
RequestLimit-UsedBereits gezählte Anfragen diesen Monat, inklusive der aktuellen. Immer numerisch.
RequestLimit-RemainingVerbleibende Anfragen diesen Monat, oder wörtlich unmetered.
RequestLimit-ResetWann der Zähler auf 0 zurückgeht: der Monatserste, 00:00 UTC.
Code
RequestLimit-Limit: 10000 RequestLimit-Used: 4231 RequestLimit-Remaining: 5769 RequestLimit-Reset: 2026-09-01T00:00:00Z

Limit und Remaining sind Strings und enthalten auf Plänen ohne Deckel das Wort unmetered statt einer Zahl. Parsen Sie defensiv — int(header) scheitert auf diesen Plänen.

Der Zähler läuft pro (Nutzer, Endpunkt, Monat). Prognose- und Historik-Anfragen haben also getrennte Budgets, und die Zahlen gelten kontoweit: Fünf Standorte abzufragen zieht aus demselben Prognose-Zähler. Das Limit selbst skaliert mit der Anzahl Ihrer Standorte — mehr Standorte bedeuten ein entsprechend größeres Budget.

Limits & Fehler

Limit / FehlerVerhalten
Forecast-ZugriffOhne Forecast-Zugang im Plan → 403.
Monatliche AnfragenMonatliches Anfragelimit (pro Nutzer & Endpunkt), Reset am Monatsersten → 429 bei Überschreitung. RequestLimit-Reset nennt den Zeitpunkt für den nächsten Versuch.
include=variability ohne Plan403, ausgelöst bevor die Anfrage gezählt wird — ein Probelauf kostet kein Kontingent.
forecast_days / past_daysWerte werden auf das Plan-Limit gekappt.
Standort nicht gefunden404.

Ihre konkreten Limits finden Sie auf der Seite über Nutzung & Limits.

Last modified on August 18, 2026
Standorte & SolarflächenHistorische Daten
On this page
  • Parameter
  • include-Gruppen
  • Was Ihr Plan erlaubt (available)
  • Antwortstruktur
  • Der strings-Block
  • Variabilitätsband (include=variability)
  • Caching, computed_at und next_poll_at
    • Wann sich eine erneute Abfrage lohnt
  • Header zum Anfragekontingent
  • Limits & Fehler
JSON
JSON
JSON
JSON