Open Weather Map API: Ein Beispiel in PHP
In einem früheren Post habe ich nach Alternativen für eine Wetter-API gesucht und eine kleine Liste der Anbieter zusammengestellt. Der Grund war die Abschaltung der Google Weather API. Weil ein Leser von Programmieren & Optimieren nach einem Tutorial zu OpenWeatherMap gebeten hat, möchte ich nun für die kostenfreie API von OpenWeatherMap (openweathermap.org) ein kleines Beispiel posten. In diesem werde ich die aktuelle Temperaturen in PHP (curl) mittels JSON Schnittstelle abfragen und darstellen.
Kurz zum Dienst selbst: Open Weather Map stellt kostenlos den Wetter Web Service zur Verfügung. Die aktuellen Wetterdaten werden von über 40000 Wetterstationen weltweit empfangen. Für die Nutzung ist keine Registrierung notwendig. Die kommerzielle Nutzung des Dienstes ist ebenfalls erlaubt. Sollte man den Dienst nutzen, würde ich einen Link zu openweathermap.org setzen, darum bittet wie ich gesehen habe auch der Anbieter selbst – selbstverständlich eigentlich. Bei einer höheren Anzahl an Abfragen (Requests) kann ein Key angefordert werden. Es gibt verschiedene Möglichkeiten die Wetterdaten zu empfangen. Da wäre einmal das JSON Format, zu welchem in diesem Artikel ein Beispiel in PHP zu finden ist, die Möglichkeit einer Abfrage vom WMS server sowie die Java Script API.
Kommen wir nun zum Beispiel. In der Dokumentation zur Open Weather Map API sind die verschiedenen Möglichkeiten der Abfrage aufgelistet. Unter anderem kann man mittels Längen- und Breitenangabe entweder nach Wetterstationen oder nach Städten suchen. Die Liste kann per Parameter dann beliebig begrenzt oder sogar in Cluster unterteilt werden. Eine weitere Möglichkeit ist die Suche nach einer Stadt ID oder nach dem Stadtnamen.
Im Beispiel suche ich nach einem Stadtnamen. Zuerst übergebe ich den Namen als GET Parameter und intialisiere eine einfach cURL-Session. Folgende URL der 2.1 API nutze ich für die Suche nach Wetterdaten einer Stadt:
http://openweathermap.org/data/2.1/find/name?q=Berlin
Hier das gesamte Script der Abfrage:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
<?php $city = $_GET['city']; if(isset($city)) { $url = 'http://openweathermap.org/data/2.1/find/name?q='.urlencode($city).'&cnt=1&lang=de'; $curl = curl_init(); $headers = array(); curl_setopt($curl, CURLOPT_HTTPHEADER, $headers); curl_setopt($curl, CURLOPT_HEADER, 0); curl_setopt($curl, CURLOPT_RETURNTRANSFER, true); curl_setopt($curl, CURLOPT_URL, $url); curl_setopt($curl, CURLOPT_TIMEOUT, 30); $json = curl_exec($curl); curl_close($curl); $data = json_decode($json); if(!empty($data->list[0]->name)) { ?> <div> Stadt: <strong><?php echo $data->list[0]->name ?></strong><br /> Aktuell: <strong><?php echo number_format($data->list[0]->main->temp - 273.15, 1, ',', '') ?> ° C </strong><br /> Temperatur (heute):<br /> min. <?php echo number_format($data->list[0]->main->temp_min - 273.15, 1, ',', '') ?> ° C<br /> max. <?php echo number_format($data->list[0]->main->temp_max - 273.15, 1, ',', '') ?> ° C </div> <?php } } ?> |
Nachdem die Daten mit der Funktion curl_exec() abgefragt und in der Variable $json abgelegt wurden, werden die Daten mit json_decode() in ein Array umgewandelt und der Variable $data zugewiesen. Anschließend erfolgt die Darstellung der Daten.
Zu beachten ist, dass die Temperaturen in Kelvin angegeben sind. Um die Daten in Grad Celsius auszugeben, substrahiert man einfach 273,15 vom jeweiligen Wert, da 0 Kelvin dem absoluten physikalischen Nullpunkt entsprechen, der in der Einheit Grad Celsius bei -273,15 liegt.
Es wird nicht nur die Temperatur geliefert, sondern auch eine Reihe weiterer Daten wie zum Beispiel Angaben zur Windrichtung und -geschwindigkeit, Bewölkung, Druck oder Luftfeuchtigkeit. Wegen der Einfachheit habe ich diese zusätzlichen Angaben weggelassen, um hauptsächlich die Nutzung zu verdeutlichen.
Hallo Peter,
danke für den Artikel und die Anleitung. Aber irgendwie scheint das nicht zu funktionieren.
Ich hab den Code in eine leere .php-Datei eingefügt und den Stadtnamen angepasst.
Als Ergebnis erhalte ich aber nur eine leere Seite. Muss ich noch was anderes beachten?
Hallo Micha, da war noch ein Leerzeichen zu viel in der Formatierung. Nach dem schließenden div-Tag muss [code]< ?[/code] durch [code]<?php[/code] ersetzt werden. Ich habe es im Artikel korrigiert. Zu beachten ist eigentlich nichts mehr, außer dass die cURL Extension in PHP vorhanden ist. Das sollte bei den meisten Webhosting-Paketen aber der Fall sein.
Hallo Peter,
hab die Änderung vorgenommen. Die cURL Extension ist auch vorhanden und aktiviert.
Aber es wird weiterhin nur eine leere Seite ausgeliefert.
Hier mal der Code
[…]
Bei mir funktioniert der Code, wenn ich ihn 1:1 übernehme. In den Kommentaren wird der Code hier zerstört. Deshalb in den Kommentaren am besten den Tag [ code ] … [ /code ] für Quellcode nutzen, ich habe Deinen leider entfernen müssen, da unlesbar.
Da eine leere Seite kommt, würde ich kontrollieren, ob display_errors gesetzt ist. Sonst auch in den ErrorLogs schauen, da müsste der Fehler auch hinterlegt sein, wenn einer vorhanden ist.
Sorry, also hier nochmal richtig:
[code]
<?php
$city = $_GET[‚Berlin‘];
if(isset($city))
{
…
[/code]
display_errors ist bei mir bei Local Value Off und bei Master Value On
Habe es auch noch einmal bei einer anderen Seite, die auch bei einem anderen Webspaceanbieter liegt, probiert. Aber auch hier das gleiche Ergebnis.
Achso. Jetzt sehe ich Dein Problem. Du hast nämlich die GET-Variable umbenannt … 😉 Das ist sogesehen falsch. Das fertige Script aus dem Artikel kannst Du folgendermaßen aufrufen:
http://www.deinedomain-xyz.de/script.php?city=Berlin
Wenn Du nur für Berlin das Wetter anzeigen lassen willst, dann muss Du aus der Zeile
[code]
$city = $_GET[‚Berlin‘];
[/code]
folgendes machen:
[code]
$city = ‚Berlin‘;
[/code]
Danach kannst Du nur die Datei
http://www.deinedomain-xyz.de/script.php
aufrufen und es wird immer das Wetter für Berlin angezeigt.
Es kommt deshalb eine weiße Seite, weil in diesem Szenario keine Stadt ausgewählt wurde. Deine Variable lautet „Berlin“. Und die ist in diesem Fall immer leer. Wenn kein Ergebnis von der API geliefert wird, dann kommt eine leere Seite.
Danke Peter, jetzt läuft es natürlich.
Hätte ich den Artikel mal etwas aufmerksamer lesen sollen 🙂
Wie kann ich die Wetter Icons auslesen? Danke
In der Antwort der API wird unter main > weather > icon der Name des jeweiligen Icons geliefert.
Hallo,
ich würde gerne den Aktuellen Status haben bzw. Leichter Regen ->
„weather“:[{„id“:500,“main“:“Rain“,“description“:“light rain“,“icon“:“10d“}]
http://openweathermap.org/data/2.1/find/name?q=Wien&cnt=1&lang=de
Kann mir jemand die variable geben? 🙂
thanks
Hallo Peter,
Habe das Script ausprobiert, und finde es super. Habe aber noch ein kleines Problem, oder ich verstehe den Zusammenhang noch nicht so ganz.
Ich möchte für das aktuelle Wetter noch das Icon abfragen. Kriege gas aber irgendwie nicht hin. Müsste doch irgendwie über „weather->icon“ gehen?
Hallo Frido,
ganz genau. Unter main > weather > icon wird nur der Name des Bildes geliefert, das zum aktuellen „Wetter“ (genauer gesagt zur „description“) passt. Eine Auflistung der von openweathermap.org fertigen Icons und deren Namen findet man hier. Ich empfehle die Bilder auf dem eigenen Webspace unter gleichem Namen abzuspeichern und entsprechend im eigenen Script zu verlinken.
@meXx
Der aktuelle Status ist unter weather -> description zu finden, sofern Du das Beispiel aus diesem Artikel verwendet hast:
$data->list[0]->weather[0]->description
$data->list[0]->weather[1]->description
…
Danke 🙂
nur leider steht dort sky is clear :(( also ich bekomm keine deutsche ausgabe 🙁
Die deutsche Ausgabe gibt es soweit ich weiß auch nicht.
Hallo,
erstmal vielen Dank für den bisher veröffentlichten Code. Funktioniert bei mir ebenfalls soweit, nur leider hänge ich etwas an der Einbindung der Grafiken fest.
Der Zusammenhang mit der Quelle ist mir bekannt, wovon das Skript die Daten bekommt. Leider hakt es bei mir bei der Einbindung im Skript an richtiger Stelle. Als Basis habe ich obigen Code genommen.
Besten Dank schon mal
Hi Peter,
vielen Dank für den Code, genau der einfache Script, den ich gesucht habe! Ideal, wenn man nur die wichtigsten Daten mit einem kleinen zusätzlichen Wetter-Icon auf seiner Webseite darstellen will. Um das Icon zu integrieren, musste ich den Code ja genau ansehen, obwohl ich von PHP Null Ahnung habe. Soweit ist alles klar, nur, was die Zahl in den eckigen Klammern bedeutet, hat sich mir nicht erschlossen.
[code]
$data->list[0]->weather[0]->…
[/code]
oder
[code]
$data->list[0]->weather[1]->…
[/code]
ergab bei meiner Testseite keinen Unterschied.
Jedenfalls wollte ich ohne Dank nicht gehen – klappt prima!
Die Zahl in der eckigen Klammer ist der Key für den jeweiligen Inhalt im „weather“ Array. Je nach Abfrage werden Wetterdaten von mehreren Wetterstationen bzw. Orten geliefert.
@Peter
einfach mal &lang=de mit übergeben dann kommt zumindest das Wetter in deutsch 😉
Hallo Peter,
ich danke auch für den Artikel und die Anleitung, aber wie bekomme ich das denn mit Vorausschau hin?
Hallo Kai, die API liefert auch eine Vorschau für die nächsten Tage, schaue in der Doku unter „weather forecast …“.
Hallo,
ich habe eine PHP Api für OpenWeatherMap geschrieben. Der Vorteil ist, dass diese alles schön in ein Wetter Objekt reinschreibt und man sich um das extrahieren der Daten aus XML / json nicht selbst kümmern muss. Ein einfaches Beispiel sieht zum Beispiel so aus:
$weather = OpenWeatherMap::getWeather(‚Berlin‘, ‚metric‘, ‚de‘);
echo $weather->temperature;
# Prints 20 °C
Vielleicht hilft es ja jemandem. Der Code steht unter der MIT Lizenz und man kann ihn sich entweder hier herunterladen: https://github.com/cmfcmf/OpenWeatherMap-PHP-Api oder composer verwenden.
Huch, da habe ich doch tatsächlich den veralteten Beispielcode kopiert. So ist es richtig: 🙂
$owm = new OpenWeatherMap();
$weather = $owm->getWeather(‚Berlin‘, ‚metric‘, ‚de‘);
echo $weather->temperature;
# Prints 20 °C
Hallo,
Leider kommen bei keine deutschsprachigen Ergebnisse an, obwohl ich die URL genauso aufgebaut habe, wie in dem Beispiel.
Kann mir jemand helfen?
$url = ‚http://openweathermap.org/data/2.1/find/name?q=‘.urlencode($city).’&cnt=1&lang=de‘;
@dominik921
Hi Dominik,
es sieht so aus, dass man das selbst machen muss. OpenWeatherM. hat wohl nur Englisch, ich werde dort einmal anfragen wie es mit deutsch aussieht.
Gr Timo
Hi,
warum werden Städte mit Umlaute (z.b. Nürnb.) nicht angezeigt im $data ->name Objekt, kann jemand helfen?
Super Arbeit Peter und cmf, hier ist meine aktuelle App: http://ph.ngrok.com/map/wetter.php .
@cmf, wie kann ich die „weather->main“ Prop. bekommen, um z.B. „Sky is clear“ zu erhalten? Du scheinst das vergessen zu haben in deinen Beispielen.
Timo