Hintergründe

Auswirkungen der DNS-Auflösung auf die Leistung der CAPTCHA-API

Kurz gesagt: In den meisten Produktions-Setups ist die DNS-Auflösung kein Performance-Problem. Wer persistente Verbindungen (HTTP-Keep-Alive) nutzt, löst den Hostnamen ocr.captchaai.com genau einmal auf und verwendet die IP für alle folgenden Anfragen wieder. Spürbar wird DNS erst dort, wo für jede Anfrage eine neue Verbindung entsteht: bei serverlosen Kaltstarts, frisch gestarteten Containern oder hoch-parallelem Lösen. Dieser Artikel zeigt, wann sich eine Optimierung lohnt – und wann Sie Ihre Zeit besser in Connection-Pooling investieren.

Wann die DNS-Auflösung überhaupt zum Flaschenhals wird

Bevor Sie irgendetwas optimieren, klären Sie, ob DNS in Ihrem Setup überhaupt eine Rolle spielt. Relevant wird die Auflösung typischerweise nur in diesen vier Fällen:

  • Neue Verbindung pro Anfrage – keine Session (Python) und kein Keep-Alive-Agent (Node.js)
  • Container- oder Serverless-Kaltstarts – frische Instanzen ohne zwischengespeichertes DNS
  • Langsame DNS-Anbieter – Standard-ISP-Resolver ohne lokalen Cache
  • Paralleles Lösen mit hohem Volumen – viele Worker starten gleichzeitig und lösen zeitgleich auf

Trifft keiner dieser Punkte auf Sie zu, ist DNS aller Wahrscheinlichkeit nach nicht Ihr Engpass – dann bringt Connection-Pooling deutlich mehr als jede DNS-Feinjustierung.

Wie viel Latenz die DNS-Auflösung kostet

Eine einzelne CAPTCHA-Lösung umfasst 5–7 HTTP-Anfragen: eine Übermittlung plus 4–6 Statusabfragen (Polling). Wird für jede dieser Anfragen neu aufgelöst, summiert sich die DNS-Zeit spürbar:

Szenario DNS-Suchen Zusätzliche Latenz
Kein Caching, langsames DNS (je 200 ms) 7 1.400 ms
DNS-Cache auf Betriebssystemebene (nur erster Aufruf) 1 200 ms
HTTP-Keep-Alive (0 neue Suchen) 0 0 ms
DNS-Vorab-Auflösung + Keep-Alive 0 0 ms

Fazit: Sobald HTTP-Keep-Alive aktiv ist, fällt DNS praktisch aus der Rechnung – dieselbe TCP-Verbindung nutzt die bereits aufgelöste IP weiter. Kritisch wird die Auflösung nur, wenn Verbindungen pro Anfrage neu aufgebaut werden.

Python: DNS-Auflösung optimieren

Aktuelles DNS-Verhalten messen

Messen Sie zuerst, bevor Sie etwas ändern. Der erste Aufruf zeigt die reine Auflösungszeit, der zweite den Effekt des OS-Caches:

import socket
import time

# Measure DNS resolution time
hostname = "ocr.captchaai.com"

start = time.time()
ip = socket.getaddrinfo(hostname, 443)
first_resolve = time.time() - start

start = time.time()
ip = socket.getaddrinfo(hostname, 443)
second_resolve = time.time() - start

print(f"First resolve: {first_resolve*1000:.1f}ms")
print(f"Second resolve: {second_resolve*1000:.1f}ms (OS cached)")

Hostnamen vorab auflösen und zwischenspeichern

Für Setups, in denen Sie ohne persistente Session arbeiten, lösen Sie den Hostnamen einmalig vorab auf und arbeiten anschließend über eine Keep-Alive-Session weiter:

import os
import socket
import requests
from urllib3.util.connection import create_connection

API_KEY = os.environ.get("CAPTCHAAI_KEY", "YOUR_API_KEY")

# Pre-resolve the API hostname
CAPTCHAAI_IP = socket.getaddrinfo("ocr.captchaai.com", 443)[0][4][0]
print(f"Resolved ocr.captchaai.com to {CAPTCHAAI_IP}")

# Patch connection to use cached IP
DNS_CACHE = {"ocr.captchaai.com": CAPTCHAAI_IP}

class CachedHTTPAdapter(requests.adapters.HTTPAdapter):
    def send(self, request, **kwargs):
        return super().send(request, **kwargs)

# Use with Session for fastest resolution
session = requests.Session()
session.headers.update({"Connection": "keep-alive"})

# The session already maintains keep-alive, so DNS is resolved once
# For the first request, the OS cache handles subsequent lookups
resp = session.get("https://ocr.captchaai.com/res.php", params={
    "key": API_KEY, "action": "getbalance", "json": "1",
})
print(f"Balance: {resp.json()}")

Einen schnelleren DNS-Resolver einsetzen

Wenn Ihr Standard-Resolver träge ist, verweisen Sie das System oder die Anwendung auf ein schnelles öffentliches DNS. Bewährt haben sich:

  • Cloudflare1.1.1.1 (löst aus den meisten Regionen in unter 10 ms auf)
  • Google Public DNS8.8.8.8
  • Quad99.9.9.9 (mit Anycast-Standorten in Europa)

Konfigurieren Sie den gewählten Resolver anschließend system- oder anwendungsseitig:

# For systems where you control DNS configuration:
# /etc/resolv.conf (Linux) or system DNS settings
# Recommended: Cloudflare (1.1.1.1) or Google (8.8.8.8)

# In Python, you can also use dnspython for explicit resolution
import dns.resolver

resolver = dns.resolver.Resolver()
resolver.nameservers = ["1.1.1.1", "8.8.8.8"]

answers = resolver.resolve("ocr.captchaai.com", "A")
for answer in answers:
    print(f"Resolved: {answer}")

Node.js: DNS-Auflösung optimieren

DNS-Auflösung messen

Dasselbe Messprinzip gilt für Node.js – der zweite Lookup profitiert vom OS-Cache:

const dns = require('dns');
const { performance } = require('perf_hooks');

const hostname = 'ocr.captchaai.com';

// First resolution
const start1 = performance.now();
dns.lookup(hostname, (err, address) => {
  const time1 = performance.now() - start1;
  console.log(`First resolve: ${time1.toFixed(1)}ms → ${address}`);

  // Second resolution (OS cached)
  const start2 = performance.now();
  dns.lookup(hostname, (err2, address2) => {
    const time2 = performance.now() - start2;
    console.log(`Second resolve: ${time2.toFixed(1)}ms → ${address2}`);
  });
});

Vorab auflösen mit Keep-Alive-Agent

Ein Keep-Alive-Agent bündelt Verbindungen und löst pro Verbindung nur einmal auf. In Kombination mit einer Vorab-Auflösung beim Start ist DNS damit aus dem kritischen Pfad:

const dns = require('dns');
const https = require('https');
const axios = require('axios');

const API_KEY = process.env.CAPTCHAAI_KEY || 'YOUR_API_KEY';

// Pre-resolve and cache
let cachedIP = null;

async function preResolve() {
  return new Promise((resolve, reject) => {
    dns.lookup('ocr.captchaai.com', (err, address) => {
      if (err) reject(err);
      cachedIP = address;
      console.log(`Cached IP: ${cachedIP}`);
      resolve(address);
    });
  });
}

// Use keep-alive agent (DNS resolved once per connection)
const agent = new https.Agent({
  keepAlive: true,
  maxSockets: 20,
  keepAliveMsecs: 60000,
});

const api = axios.create({
  baseURL: 'https://ocr.captchaai.com',
  httpsAgent: agent,
  timeout: 30000,
});

(async () => {
  await preResolve();
  const resp = await api.get('/res.php', {
    params: { key: API_KEY, action: 'getbalance', json: '1' },
  });
  console.log(`Balance: ${resp.data}`);
})();

Serverless- und Container-Umgebungen

Genau hier zahlt sich die Vorab-Auflösung am stärksten aus, weil jeder Kaltstart den Cache verwirft:

Umgebung DNS-Cache-Verhalten Empfehlung
AWS Lambda Im Ausführungskontext zwischengespeichert, beim Kaltstart verloren Vorab-Auflösung in der Handler-Initialisierung
Google Cloud Functions Innerhalb der Instanz zwischengespeichert Vorab-Auflösung im globalen Scope
Docker Nutzt standardmäßig das Host-DNS --dns 1.1.1.1 konfigurieren
Kubernetes CoreDNS mit konfigurierbarem Cache ndots: 1 in der Pod-DNS-Konfiguration setzen

Für DACH-Deployments heißt das konkret: Wer seine Worker etwa auf Hetzner Cloud, netcup oder IONOS betreibt, sollte prüfen, welchen Resolver die Instanz standardmäßig verwendet. Ein VPS in einem Hetzner-Rechenzentrum in Nürnberg oder Falkenstein löst über den providereigenen Resolver in der Regel schnell auf – bei frisch gestarteten Containern ohne warmen Cache lohnt es sich dennoch, 1.1.1.1 oder 8.8.8.8 explizit zu setzen und den Hostnamen einmal vorab aufzulösen.

Fehlerbehebung

Die folgende Tabelle ordnet die häufigsten Latenzsymptome ihrer wahrscheinlichen DNS-Ursache zu – und nennt jeweils die schnellste Gegenmaßnahme:

Problem Ursache Lösung
Erste API-Anfrage langsam, alle weiteren schnell DNS-Suche beim ersten Aufruf Normal bei OS-Caching; Keep-Alive verwenden
Alle Anfragen langsam (~100 ms+ zusätzlich) Kein DNS-Caching, langsamer Resolver DNS auf 1.1.1.1 oder 8.8.8.8 setzen
Unregelmäßige Latenzspitzen Ablauf der DNS-Cache-TTL Lokale Cache-TTL erhöhen oder vorab auflösen
Container-Kaltstart langsam Kein zwischengespeichertes DNS auf neuer Instanz Im Initialisierungscode vorab auflösen

Häufige Fragen

Lohnt sich DNS-Caching, wenn ich bereits Connection-Pooling nutze?

Meist nein. Bei aktivem Connection-Pooling mit Keep-Alive wird der Hostname einmal aufgelöst und die Verbindung wiederverwendet – DNS liegt dann nicht mehr im kritischen Pfad. Der Aufwand lohnt sich vor allem in serverlosen Umgebungen und bei Verbindungen pro Anfrage.

Warum ist die erste API-Anfrage nach einem Kaltstart langsamer?

Weil die frische Instanz keinen warmen DNS-Cache besitzt und den Hostnamen erst auflösen muss. Lösen Sie ocr.captchaai.com bereits im Initialisierungscode (Handler-Init bzw. globaler Scope) vorab auf, dann trifft der Mehraufwand nicht die erste echte Anfrage.

Wie erkenne ich, ob DNS der Engpass ist und nicht der Solver?

Messen Sie die reine Auflösungszeit mit dem Mess-Snippet oben und vergleichen Sie sie mit der Gesamt-Antwortzeit. Liegen zwischen den Läufen nur die DNS-Suchen und nicht die Lösungszeit auseinander, ist DNS die Ursache. Die Lösungszeit selbst hängt vom CAPTCHA-Typ ab, nicht von DNS.

Beeinflusst die DNS-TTL die Latenz zwischen einzelnen Läufen?

Ja. Läuft die TTL des lokalen Caches zwischen zwei Läufen ab, wird neu aufgelöst und die Latenz springt kurzzeitig. Persistente HTTP-Sessions mit Connection-Pooling oder eine Vorab-Auflösung glätten diese Spitzen zuverlässig.

Nächste Schritte

Der pragmatische Ablauf für die meisten Setups:

  1. Mit dem Mess-Snippet prüfen, ob die reine Auflösungszeit in Ihrem Workflow überhaupt ins Gewicht fällt.
  2. HTTP-Keep-Alive aktivieren, damit ocr.captchaai.com pro Verbindung nur ein einziges Mal aufgelöst wird.
  3. In serverlosen Umgebungen den Hostnamen bereits im Initialisierungscode (Handler-Init bzw. globaler Scope) vorab auflösen.

Danach liegt DNS nicht mehr im kritischen Pfad – die verbleibende Optimierungszeit ist in Connection-Pooling und Wiederholungslogik deutlich besser investiert.

Verwandte Leitfäden

Kommentare sind für diesen Artikel deaktiviert.