Sans KYC — pas d’ID, pas de selfie, pas de documents. Payer en crypto : BTC, USDT, USDC, ETH, SOL, LTC
Langue: Français
Commencez

Docs · concurrence · débit · courtoisie

Concurrence et débit grâce aux proxy résidentiels

La passerelle facture par GB, pas par thread, donc votre véritable limite est chaque site cible. Dimensionnez la concurrence selon le débit dont vous avez besoin, limitez-la par hôte, et laissez les réponses vous indiquer quand ralentir.

Dernière mise à jour: · 6 min de lecture

Réponse rapide

Combien de requêtes simultanées puis-je lancer via des proxy résidentiels ?

Autant que chaque cible le tolère : CrawlRelay facture le trafic résidentiel par GB (0,50 $US/GB à partir de 50 GB), pas par thread ou connexion. Dimensionnez la concurrence avec la loi de Little, requêtes en cours = pages par seconde × secondes par page, puis limitez-la par hôte, en commençant à 2-4. Réduisez-la si des réponses 429 ou 503 apparaissent. Paiement en crypto, sans KYC.

La concurrence en un coup d'œil

FacturationPar GB de trafic ; threads et connexions ne sont pas facturés
Règle de dimensionnementEn vol = débit × latence (loi de Little)
Point de départ par hôte2 à 4 requêtes parallèles ; 1 avec délai pour petits sites
Signaux pour ralentir429, 503, augmentation des temps de réponse, pages de challenge
Calcul de bande passantePages par seconde × octets par page × 3 600 = octets par heure
Réponse médiane résidentielle0,93 s sur le réseau proxy, 3,21 s sur cibles réelles (Proxyway 2026)

Comment dimensionner la concurrence selon le débit dont j'ai besoin ?

Utilisez la loi de Little : le nombre de requêtes en vol est égal au taux désiré multiplié par la durée moyenne d'une requête. La recherche Proxyway Proxy Market Research 2026 a mesuré une médiane de 3,21 secondes par requête sur cibles réelles via proxy résidentiel, prévoyez donc entre 2 à 4 secondes par site réel, pas seulement la valeur de moins d'une seconde du réseau seul.

ObjectifTemps par requêteRequêtes en vol
5 pages par seconde2 s10
20 pages par seconde2 s40
20 pages par seconde4 s80
100 pages par seconde3 s300

Puis répartissez ces requêtes entre les hôtes. Quarante requêtes en vol réparties sur 200 sites est raisonnable ; quarante sur un seul petit site constitue un test de charge qu'il n'a jamais accepté.

Quelle bande passante consomme ce débit ?

Multipliez pages par seconde par octets par page. À 20 pages HTML par seconde et 50 KB par page, le crawl déplace 1 MB par seconde, soit 3,6 GB par heure et environ 86 GB par jour. À 2 MB par page rendue, le même débit consommerait 40 MB par seconde.

Multipliez le résultat par le prix par GB de votre forfait, 0,50 $US/GB à partir de 50 GB à CrawlRelay, pour obtenir le coût horaire. Le guide du calculateur de bande passante fournit les poids typiques des pages selon leur type.

Quelles limites par hôte dois-je initialiser ?

CibleRequêtes parallèles par hôteDélai entre requêtesNotes
Petit site (blog, commerce local)12–5 sRespectez Crawl-delay dans le robots.txt si présent
Site moyen2–40,5–2 sSurveillez les temps de réponse ; ralentissez quand ils doublent
Grande plateforme avec CDN4–16AutoThrottle ou adaptatifAugmentez uniquement tant que les taux 429 et 5xx restent stables
API publiqueLa limite documentéeComme indiqué dans la documentationUtilisez la clé API et les limites fournies par le fournisseur

Comment adapter automatiquement la concurrence ?

Utilisez une augmentation additive et une diminution multiplicative, la règle TCP pour la congestion : ajoutez un slot après une série de réponses sans erreur, divisez la limite par deux en cas de 429 ou 503. Le limiteur ci-dessous garde une limite par hôte, pause chaque requête vers cet hôte pendant le délai Retry-After, retente une fois, et ne dépasse jamais un plafond fixé. Les erreurs réseau sont retournées en valeurs, ainsi un timeout n’arrête pas le lot.

Python asyncio : limite adaptative avec httpx
import asyncio
import random
from urllib.parse import urlsplit

import httpx

PROXY = "http://USERNAME-country-us:[email protected]:7777"


class AdaptiveLimit:
    """One per host: +1 slot after 20 clean responses, halve on 429/503, pause for Retry-After."""

    def __init__(self, start=2, low=1, high=16):
        self.limit, self.low, self.high = start, low, high
        self.in_flight, self.clean = 0, 0
        self.pause_until = 0.0
        self.cond = asyncio.Condition()

    async def __aenter__(self):
        loop = asyncio.get_running_loop()
        while True:
            async with self.cond:
                await self.cond.wait_for(lambda: self.in_flight < self.limit)
                delay = self.pause_until - loop.time()
                if delay <= 0:
                    self.in_flight += 1
                    return self
            await asyncio.sleep(delay)  # the host asked for a pause: wait outside the lock

    async def __aexit__(self, *exc):
        async with self.cond:
            self.in_flight -= 1
            self.cond.notify_all()

    def record(self, status, retry_after=None):
        if status in (429, 503):
            self.limit, self.clean = max(self.low, self.limit // 2), 0
            wait = int(retry_after) if retry_after and retry_after.isdigit() else 5 + random.random()
            now = asyncio.get_running_loop().time()
            self.pause_until = max(self.pause_until, now + wait)
        elif status < 400:
            self.clean += 1
            if self.clean >= 20 and self.limit < self.high:
                self.limit, self.clean = self.limit + 1, 0


gates = {}


def gate_for(url):
    host = urlsplit(url).hostname
    if host not in gates:
        gates[host] = AdaptiveLimit()
    return gates[host]


async def fetch(client, url, attempts=2):
    gate = gate_for(url)
    status = None
    for _ in range(attempts):
        try:
            async with gate:
                r = await client.get(url)
        except httpx.HTTPError as exc:
            return "error: %s" % type(exc).__name__
        status = r.status_code
        gate.record(status, r.headers.get("Retry-After"))
        if status not in (429, 503):
            break  # the retry, if any, waits for the host's pause in __aenter__
    return status


async def main(urls):
    timeout = httpx.Timeout(30.0, connect=10.0)
    async with httpx.AsyncClient(proxy=PROXY, timeout=timeout) as client:
        print(await asyncio.gather(*(fetch(client, u) for u in urls)))
    print({host: gate.limit for host, gate in gates.items()})


asyncio.run(main(["https://example.com/"] * 10))

Qu’est-ce qui ralentit un crawl via proxy à part la cible ?

  • Poignées de main TLS. Une nouvelle connexion par requête, nécessaire pour une nouvelle IP à chaque fois, implique une poignée de main avec le site à chaque fois. Gardez une session persistante avec keep-alive pour les pages d’un même site quand la diversité IP n’a pas d’importance.
  • Sorties lentes. Les sorties résidentielles et mobiles sont des connexions domestiques et cellulaires réelles. Utilisez des timeouts et réessayez sur une nouvelle connexion plutôt que d’attendre.
  • Ciblage étroit. Une petite ville ou un seul ASN a moins de sorties qu’un pays. Ciblez précisément uniquement là où les données changent.
  • Rendu. Un navigateur sans interface graphique consomme beaucoup plus de CPU, mémoire et trafic par page qu’un client HTTP. Rendez seulement les pages nécessitant JavaScript.
  • DNS. Avec socks5h:// ou le port HTTP, la résolution DNS se fait à la sortie ; vous n’avez pas besoin d’un cache de résolveur local pour les hôtes cibles.

Questions sur la concurrence

CrawlRelay limite-t-il le nombre de threads ou connexions ?

Les forfaits se facturent au GB de trafic, pas par thread, connexion ou requête, et les plans publiés ne limitent pas le nombre de threads. Les limites pratiques sont la tolérance de chaque cible et votre propre machine. Pour un crawl très volumineux, écrivez d’abord à [email protected] pour qu’on vérifie la couverture de votre ciblage.

Pourquoi mon crawl est-il devenu plus lent après avoir ajouté des threads ?

Habituellement parce que la cible commence à vous limiter : les temps de réponse montent, des réponses 429 ou 503 apparaissent, les réessais ajoutent de la charge. L’autre cause fréquente est que votre machine manque de CPU ou de sockets, surtout avec les navigateurs sans interface graphique. Mesurez la latence et les taux d’erreur par hôte avant d’ajouter des threads.

Une connexion par requête est-elle plus lente que keep-alive ?

Oui, en raison d’une poignée de main TCP et TLS par requête, généralement quelques centaines de millisecondes via une sortie résidentielle. C’est le coût d’une nouvelle IP à chaque requête. Pour de nombreuses pages sur un même site où l’IP importe peu, une session persistante avec keep-alive est plus rapide et consomme moins de trafic.

Comment respecter le crawl-delay robots.txt dans un crawler concurrent ?

Analysez robots.txt une fois par hôte, mettez-le en cache jusqu’à 24 heures comme suggéré par la RFC 9309, et transformez une valeur Crawl-delay en un intervalle minimal par hôte entre les requêtes avec une concurrence de 1. Le Python urllib.robotparser l’expose via crawl_delay().

Évoluer avec la tarification au GB

0,50 $US/GB de 50 GB à 1 TB, trafic qui n’expire jamais.

À partir de 0,50 $US/GB · sans KYC

Commencez