Mit externen APIs können Python-Entwickler Datenabruf, Finanzinformationen und Bildverarbeitung implementieren, ohne alles von Grund auf zu bauen. „Kostenlos nutzbar“ und „sicher in Produktion einsetzbar“ sind jedoch zwei völlig unterschiedliche Dinge.
Dieser Artikel stellt 10 praktische kostenlose APIs für Python vor — mit produktionsreifem Code, Rate-Limit-Details und Sicherheitsdesign-Mustern. Über eine einfache API-Liste hinaus behandeln wir die Designphilosophie, die Profis bei der Arbeit mit externen APIs anwenden.
Zielniveau: Anfänger bis Fortgeschrittene (Kenntnis von requests). Voraussetzung:
pip install requests
Für sichere API-Schlüsselverwaltung siehe auch „10 Python-Sicherheitsimplementierungsmuster„.
Grundvorlage für API-Aufrufe
Bevor wir uns einzelnen APIs widmen, etablieren wir die Basismuster-Vorlage, die jeder API-Aufruf befolgen sollte. In Produktion sind diese vier Punkte der Mindeststandard:
- Timeout setzen — verhindert, dass Ihr Programm endlos wartet
- Statuscodes prüfen — nicht-200-Antworten korrekt behandeln
- Ausnahmen behandeln — mit Netzwerkfehlern und Timeouts umgehen
- Nicht von JSON ausgehen — Abstürze vermeiden, wenn die Antwort HTML oder Text ist
import requests
url = "https://api.example.com/data"
try:
response = requests.get(url, timeout=5)
response.raise_for_status()
data = response.json()
print(data)
except requests.exceptions.Timeout:
print("Timeout: server not responding")
except requests.exceptions.HTTPError as e:
print(f"HTTP error: {e.response.status_code}")
except requests.exceptions.RequestException as e:
print(f"Request error: {e}")
except ValueError:
print("JSON decode error: response is not JSON")
Behalten Sie diese Vorlage als gemeinsame Hilfsfunktion in Ihrem Projekt. Die Codebeispiele unten lassen die Fehlerbehandlung der Kürze halber weg, wenden Sie dieses Muster aber immer in Produktionscode an.
Vergleichstabelle Kostenloser APIs
| API | Zweck | API-Schlüssel | Rate Limit | Kommerziell | Schwierigkeit |
|---|---|---|---|---|---|
| ① Open-Meteo | Wetterdaten | Keiner | Locker | Ja | ★☆☆ |
| ② ExchangeRate | Wechselkurse | Keiner | 1.500/Tag | Ja | ★☆☆ |
| ③ CoinGecko | Kryptopreise | Keiner | 10–30/Min | AGB prüfen | ★☆☆ |
| ④ JSONPlaceholder | Test/Mock | Keiner | Keiner | — | ★☆☆ |
| ⑤ REST Countries | Länderinformationen | Keiner | Locker | Ja | ★☆☆ |
| ⑥ The Cat API | Katzenbilder | Optional | 10/Min | Ja | ★☆☆ |
| ⑦ IP-API | IP-Geolokalisierung | Keiner | 45/Min | Nur kostenpflichtig | ★☆☆ |
| ⑧ Advice Slip | Zufällige Zitate | Keiner | 1/2 Sek | Ja | ★☆☆ |
| ⑨ PokeAPI | Pokémon-Daten | Keiner | Locker | Ja | ★★☆ |
| ⑩ Numbers API | Zahlen-Trivia | Keiner | Locker | Ja | ★☆☆ |
① Open-Meteo — Wetter-API ohne Schlüssel
Open-Meteo ist eine vollständig kostenlose Wetterdaten-API ohne API-Schlüssel. Sie liefert aktuelles Wetter, Temperatur, Windgeschwindigkeit, Niederschlag und Vorhersagen bis zu 16 Tage im Voraus. Kommerzielle Nutzung ist erlaubt — die erste Wahl für wetterbezogene Tools.
import requests
url = "https://api.open-meteo.com/v1/forecast"
params = {
"latitude": 35.6762,
"longitude": 139.6503,
"current_weather": True
}
response = requests.get(url, params=params, timeout=5)
data = response.json()
weather = data["current_weather"]
print(f"Temp: {weather['temperature']}°C")
print(f"Wind: {weather['windspeed']} km/h")
Der größte Vorteil ist sofortiger Datenzugriff ohne Authentifizierung. Keine API-Schlüssel-Registrierung oder Kontoerstellung nötig. Ändern Sie Breiten-/Längengrad und Sie erhalten Wetterdaten von überall auf der Welt.
Open-Meteo ist ein Open-Source-Projekt mit Daten europäischer Wetterdienste. Die Genauigkeit ist auch für Standorte in Asien und Amerika hoch — geeignet für private Projekte und kommerzielle Tools.
② ExchangeRate API — Wechselkurse
ExchangeRate API bietet kostenlose Devisenkurse für wichtige Währungen. Nützlich für Währungsumrechner, Preisvergleichsseiten und Finanz-Dashboards. Kein API-Schlüssel erforderlich, 1.500 Anfragen pro Tag.
import requests
url = "https://open.er-api.com/v6/latest/USD"
response = requests.get(url, timeout=5)
data = response.json()
jpy_rate = data["rates"]["JPY"]
print(f"1 USD = {jpy_rate} JPY")
# Currency conversion example
usd_amount = 100
jpy_amount = usd_amount * jpy_rate
print(f"{usd_amount} USD = {jpy_amount:.0f} JPY")
Bei Finanzdaten ist die Aktualisierungsfrequenz entscheidend. Diese API aktualisiert etwa einmal täglich — ungeeignet für Echtzeit-Handel. Für ungefähre Währungsumrechnung und tägliche Preisreferenzen reicht die Genauigkeit aus.
Bei der Anzeige von Wechselkursen für Nutzer immer „Kurse sind ungefähr“ angeben. Abweichungen von Echtzeitkursen sind möglich; diese Daten dürfen nicht als Grundlage für Finanztransaktionen dienen.
③ CoinGecko API — Kryptowährungspreise
CoinGecko liefert Kryptowährungspreise, Marktkapitalisierung, Handelsvolumen und Rankings. Der kostenlose Plan ist überraschend leistungsstark und wird häufig für kryptobezogene Tool-Entwicklung genutzt.
import requests
url = "https://api.coingecko.com/api/v3/simple/price"
params = {
"ids": "bitcoin,ethereum",
"vs_currencies": "usd,eur",
"include_24hr_change": "true"
}
response = requests.get(url, params=params, timeout=5)
data = response.json()
btc = data["bitcoin"]
print(f"BTC: ${btc['usd']:,.0f} (24h: {btc['usd_24h_change']:.1f}%)")
CoinGecks Rate Limit im kostenlosen Plan liegt bei etwa 10–30 Anfragen pro Minute. Da Kryptopreise volatil sind, ist Caching unerlässlich. Daten jede Minute abrufen, lokal speichern und aus dem Cache ausliefern.
CoinGecko unterstützt den Abruf mehrerer Währungen in einer Anfrage. Nutzen Sie ids=bitcoin,ethereum,solana mit Kommatrennung, um die Anfrageanzahl deutlich zu reduzieren.
④ JSONPlaceholder — Der Standard für API-Übungen
JSONPlaceholder ist eine Mock-API für REST-API-Lernen und -Tests. Sie liefert simulierte Daten für Benutzer, Beiträge, Kommentare und Alben — weit verbreitet für API-Entwicklungs-Prototyping und Frontend-Tests.
import requests
# Get posts
url = "https://jsonplaceholder.typicode.com/posts"
params = {"_limit": 3}
response = requests.get(url, params=params, timeout=5)
posts = response.json()
for post in posts:
print(f"[{post['id']}] {post['title']}")
# Practice POST requests
new_post = {"title": "Test", "body": "Hello", "userId": 1}
res = requests.post(url, json=new_post, timeout=5)
print(f"Created: status={res.status_code}")
Der größte Vorteil ist Unterstützung aller HTTP-Methoden: GET, POST, PUT, PATCH, DELETE. POST- und DELETE-Anfragen ändern keine echten Daten — Antworten sind simuliert, sicheres Experimentieren möglich. Ideal für Onboarding neuer Entwickler und API-Client-Tests.
Wenn Sie eine Mock-API für Ihr eigenes Projekt brauchen, nutzen Sie JSONPlaceholders Design als Referenz und richten Sie einen lokalen Mock-Server mit json-server (npm-Paket) ein.
⑤ REST Countries — Länderinformationen
REST Countries liefert grundlegende Informationen zu jedem Land der Welt — Bevölkerung, Fläche, Hauptstadt, Flagge, Währung, Sprachen und Region — alles im JSON-Format. Ideal für Geografie-Bildungstools, Statistik-Dashboards und internationalisierte Anwendungen.
import requests
url = "https://restcountries.com/v3.1/name/japan"
response = requests.get(url, timeout=5)
data = response.json()[0]
print(f"Country: {data['name']['common']}")
print(f"Capital: {data['capital'][0]}")
print(f"Population: {data['population']:,}")
print(f"Region: {data['region']}")
print(f"Flag: {data['flag']}")
Diese API ist ideal zum Cachen, da Länderdaten sich selten ändern. Alle Daten einmal abrufen und lokal speichern — kein erneuter API-Aufruf nötig. Alle Daten beim Start in den Speicher laden ist der effizienteste Ansatz.
Der Endpunkt /v3.1/all liefert Daten für alle 250+ Länder auf einmal. Nutzen Sie Feldfilter (?fields=name,population,capital), um die Antwortgröße zu reduzieren und Bandbreite zu sparen.
⑥ The Cat API — Zufällige Katzenbilder
The Cat API liefert zufällige Katzenbilder. Obwohl spielerisch, ist sie in Produktion nützlich für UI-Bildanzeige-Tests, dynamische Platzhalter-Generierung und API-Client-Tests.
import requests
url = "https://api.thecatapi.com/v1/images/search"
params = {"limit": 3}
response = requests.get(url, params=params, timeout=5)
images = response.json()
for img in images:
print(f"URL: {img['url']} (size: {img['width']}x{img['height']})")
Grundfunktionen funktionieren ohne API-Schlüssel; eine kostenlose Registrierung erhöht die Rate Limits und schaltet Rassenfilter sowie Favoriten frei.
Beim Testen von „dynamischer Bildanzeige“-Funktionen in der Frontend-Entwicklung bietet diese API eine realistischere Testumgebung als statische Dummy-Bilder.
⑦ IP-API — IP-Geolokalisierung
IP-API liefert Geolokalisierungsdaten aus IP-Adressen — Land, Region, Stadt, ISP und Zeitzone. Verwendet für Zugriffsanalysen, regionsbasierte Inhaltsanzeige und Sicherheitsüberwachung.
import requests
url = "http://ip-api.com/json/"
response = requests.get(url, timeout=5)
data = response.json()
print(f"Country: {data['country']}")
print(f"Region: {data['regionName']}")
print(f"City: {data['city']}")
print(f"ISP: {data['isp']}")
print(f"Timezone: {data['timezone']}")
Die kostenlose Stufe ist nur HTTP (HTTPS erfordert einen kostenpflichtigen Plan). Für Produktionsumgebungen mit HTTPS-Anforderung: Upgrade erwägen oder zu Alternativen wie ipinfo.io wechseln. Kommerzielle Nutzung erfordert ebenfalls den kostenpflichtigen Plan.
Rate Limit: 45 Anfragen pro Minute. Für Batch-IP-Abfragen den Endpunkt http://ip-api.com/batch für bessere Effizienz nutzen.
⑧ Advice Slip API — Zufällige Zitate
Advice Slip API liefert zufällige Ratschläge und Zitate auf Englisch. Nützlich für UI-Testanzeigen, tägliche Nachrichten-Funktionen und Chatbot-Ausschmückungen.
import requests
url = "https://api.adviceslip.com/advice"
response = requests.get(url, timeout=5)
data = response.json()
advice = data["slip"]["advice"]
print(f"Today's advice: {advice}")
Diese API zeichnet sich durch ein minimalistisches Endpunkt-Design aus — nur /advice (zufällig) und /advice/{id} (per ID). Ein 2-Sekunden-Intervall-Limit gilt zwischen aufeinanderfolgenden Aufrufen.
APIs mit „ein Endpunkt, eine Antwort“-Design wie dieses dienen als Lehrbuch-Referenz für API-Design. Beim Bau eigener APIs ist ein so einfacher Start eine Produktions-Best-Practice.
⑨ PokeAPI — Ideal zum Lernen Strukturierter Daten
PokeAPI liefert Pokémon-Namen, Typen, Stats und Bilder. Über Spieldaten hinaus eignet sich die Struktur hervorragend zum Lernen von verschachtelter JSON-Verarbeitung, Paginierung und relationaler Datenbehandlung — Muster, die Sie in jeder Produktions-API antreffen.
import requests
url = "https://pokeapi.co/api/v2/pokemon/pikachu"
response = requests.get(url, timeout=5)
data = response.json()
print(f"Name: {data['name']}")
print(f"Type: {data['types'][0]['type']['name']}")
print(f"HP: {data['stats'][0]['base_stat']}")
print(f"Image: {data['sprites']['front_default']}")
PokeAPI-Antworten sind tief verschachtelt — Zugriffsmuster wie data["types"][0]["type"]["name"] sind nötig. Das ist bei Produktions-APIs (Stripe, Twilio, AWS SDK) üblich; Übung hier macht die reale API-Integration reibungsloser.
PokeAPI hat über 1.000 Einträge mit Paginierung (?offset=20&limit=20). Das Listen-→-Detail-Muster gilt direkt für E-Commerce- und Social-Media-API-Design.
⑩ Numbers API — Zahlen-Trivia
Numbers API liefert Trivia und witzige Fakten zu beliebigen Zahlen. Nützlich für Bildungsseiten, Quiz-Tools und UI-Ausschmückung mit täglichem Inhalt.
import requests
number = 42
url = f"http://numbersapi.com/{number}?json"
response = requests.get(url, timeout=5)
data = response.json()
print(f"{number}: {data['text']}")
# e.g.: 42: 42 is the answer to the Ultimate Question ...
Typen: trivia (Standard), math, date und year. Beispiel: http://numbersapi.com/3/14/date?json liefert Trivia zum 14. März.
Numbers API ist nur HTTP — keine HTTPS-Unterstützung. Für Produktion entweder vermeiden oder Anfragen über Ihren Server weiterleiten und HTTPS-Antworten an Clients zurückgeben.
Rate Limits und Caching-Strategie
Die gefährlichste Falle bei kostenlosen APIs ist das Überschreiten von Rate Limits. Kostenlose Dienste haben strenge Limits; Verstöße führen zu IP-Sperren, die Stunden oder Tage dauern können.
Typische Rate-Limit-Muster:
| Muster | Beispiel | Anwendungsfall |
|---|---|---|
| Pro Sekunde | 1/Sek | Echtzeitdaten |
| Pro Minute | 60/Min | Standard-APIs |
| Pro Tag | 1.000/Tag | Datenabruf |
Die Lösung ist Caching. API-Antworten lokal speichern und innerhalb eines TTL-Fensters aus dem Cache ausliefern.
import requests
import time
import json
import os
CACHE_FILE = "cache.json"
CACHE_TTL = 300 # 5 Minuten
def get_with_cache(url):
if os.path.exists(CACHE_FILE):
with open(CACHE_FILE) as f:
cache = json.load(f)
if url in cache and time.time() - cache[url]["time"] < CACHE_TTL:
return cache[url]["data"]
response = requests.get(url, timeout=5)
data = response.json()
cache = {}
if os.path.exists(CACHE_FILE):
with open(CACHE_FILE) as f:
cache = json.load(f)
cache[url] = {"data": data, "time": time.time()}
with open(CACHE_FILE, "w") as f:
json.dump(cache, f)
return data
In Produktion Redis oder memcached statt Datei-Caching nutzen. Django bietet django.core.cache, FastAPI hat aiocache für eingebaute Cache-Unterstützung.
Essentielle Sicherheitsdesign-Muster
Produktionscode mit externen APIs erfordert diese fünf Designmuster:
| Muster | Zweck | Risiko bei Fehlen |
|---|---|---|
| timeout | Endloses Warten verhindern | Programm friert ein |
| retry | Vorübergehende Fehler behandeln | Verarbeitung stoppt |
| rate control | API-Limits einhalten | IP-Sperre |
| fallback | Bei API-Ausfällen | Dienstausfall |
| cache | Anfragen reduzieren | Limit überschritten |
Ein kombiniertes Produktionsmuster:
import requests
import time
def safe_api_call(url, max_retries=3, delay=1):
for attempt in range(max_retries):
try:
response = requests.get(url, timeout=5)
if response.status_code == 429: # Rate Limit
wait = int(response.headers.get("Retry-After", delay * 2))
time.sleep(wait)
continue
response.raise_for_status()
return response.json()
except requests.exceptions.RequestException:
if attempt < max_retries - 1:
time.sleep(delay * (attempt + 1))
continue
return None # fallback
return None
Merken Sie sich dieses Produktionsprinzip: Externe APIs sind standardmäßig unzuverlässig. Ausfälle, Spez-Änderungen, Latenzspitzen, Limit-Änderungen — das sind keine „könnte passieren“-Szenarien, sondern „wird passieren“. Profis entwerfen unter der Annahme, dass externe APIs nicht vertrauenswürdig sind.
Mehr zu sicherem Design: „10 Python-Sicherheitsimplementierungsmuster„.
Häufige Fehler und Nutzungsbedingungen
Kennen Sie die Fehlermuster, die Anfänger häufig treffen:
| Fehler | Ergebnis | Lösung |
|---|---|---|
| API-Aufrufe in Schleife | IP-Sperre | sleep + Cache |
| Kein Caching | Rate-Limit überschritten | Datei-/Redis-Cache |
| Keine Fehlerbehandlung | Programmabsturz | try/except erforderlich |
| Kein Timeout | Programm friert ein | timeout=5 als Standard |
| ToS ignorieren | Rechtliches Risiko | Nutzungsbedingungen lesen |
Prüfen Sie immer die Nutzungsbedingungen. Auch kostenlose APIs können Einschränkungen haben:
- Keine kommerzielle Nutzung — nur private Nutzung
- Namensnennung erforderlich — „Powered by ○○“-Anzeige verpflichtend
- Keine Weiterverbreitung — Rohdaten nicht auf anderem Dienst veröffentlichen
- HTTPS-Einschränkungen — kostenlose Stufe nur HTTP (IP-API, Numbers API)
„Kostenlos“ bedeutet nicht „beliebig nutzbar“. Nutzungsbedingungen zu ignorieren ist gefährlicher als fehlerhaften Code auszuliefern — es ist ein direktes rechtliches Risiko.
Professionelles Design — Provider Abstraction
Erfahrene Entwickler denken über externe APIs so:
- Kostenlose APIs sind für Prototyping und Validierung
- Migration auf kostenpflichtige Stufe oder selbst-gehosteten Ersatz in Produktion planen
- Design zur Vermeidung von Überabhängigkeit von einem einzelnen Anbieter
Das erreicht man durch Provider Abstraction — API-Aufrufe hinter einer Schnittstelle kapseln, sodass Anbieter gewechselt werden können, ohne Anwendungscode zu ändern.
class WeatherProvider:
def get_temperature(self, lat, lon):
raise NotImplementedError
class OpenMeteoProvider(WeatherProvider):
def get_temperature(self, lat, lon):
url = f"https://api.open-meteo.com/v1/forecast?latitude={lat}&longitude={lon}¤t_weather=true"
data = requests.get(url, timeout=5).json()
return data["current_weather"]["temperature"]
class PaidWeatherProvider(WeatherProvider):
def get_temperature(self, lat, lon):
# Swap to paid API by changing just this class
pass
# Usage
weather = OpenMeteoProvider()
temp = weather.get_temperature(35.67, 139.65)
print(f"Temperature: {temp}°C")
Mit diesem Design erfordert der Wechsel von API-Anbietern nur die Änderung einer Klasse. Kein Umschreiben der gesamten Anwendung. Beim Testen können Sie auch einen Mock-Provider einsetzen.
Bekannt auch als „Strategy Pattern“ — gilt über APIs hinaus für Datenbanken, E-Mail-Dienste, Dateispeicher — jede externe Service-Integration.
Häufig Gestellte Fragen
F: Was ist der Unterschied zwischen APIs mit und ohne Schlüssel?
API-Schlüssel identifizieren Nutzer. Schlüssellose APIs sind bequem, haben aber tendenziell strengere IP-basierte Rate Limits. APIs mit Schlüsseln können Limits pro Nutzer verwalten und erlauben typischerweise mehr Anfragen.
F: Kann ich mit kostenlosen APIs einen öffentlichen Dienst bauen?
Das hängt von den Nutzungsbedingungen ab. Open-Meteo und REST Countries erlauben kommerzielle Nutzung, aber die kostenlose Stufe von IP-API ist nur nicht-kommerziell. Prüfen Sie vor der Veröffentlichung immer die ToS jeder API.
F: Was, wenn eine API plötzlich ausfällt?
Genau deshalb ist Fallback-Design wichtig. Aktuelle Daten im Cache halten, um sie bei Ausfällen ausliefern zu können. Bei längerer Downtime Provider Abstraction nutzen, um auf eine alternative API zu wechseln.
F: Was bedeutet 429 Too Many Requests?
Sie haben das Rate Limit überschritten. Prüfen Sie den Retry-After-Antwort-Header und warten Sie die angegebenen Sekunden vor dem erneuten Versuch. Bei wiederholtem 429: Caching implementieren oder Anfrageintervalle erhöhen.
Fazit
Kostenlose APIs ermöglichen Python-Entwicklern Wetter, Devisen, Krypto, Bilder und unzählige weitere Funktionen in Rekordzeit. Aber was wirklich zählt, ist nicht welche APIs Sie wählen — sondern wie Sie sie nutzen.
- Immer Timeout und Fehlerbehandlung implementieren
- Rate Limits prüfen und mit Caching einhalten
- Nutzungsbedingungen vor Nutzung jeder API lesen
- Abhängigkeiten mit Provider Abstraction verwalten
- Unter der Annahme entwerfen, dass externe APIs unzuverlässig sind
APIs sind mächtig, aber Überabhängigkeit bricht Dinge. Mit Bedacht genutzt können sie Ihre Entwicklungsgeschwindigkeit deutlich beschleunigen. Das ist die Essenz externer API-Integration.

Schreibe einen Kommentar