Guide got-scraping avec Node.js : proxies résidentiels et header generator

Apprenez à utiliser got-scraping avec Node.js pour des requêtes HTTP qui ressemblent à un vrai navigateur, avec rotation de proxies résidentiels ProxyHat, hooks de retry et patterns de production.

got-scraping in Node.js: A Developer's Guide with Residential Proxies
Dans cet article

Pourquoi got-scraping avec Node.js change la donne

Si vous avez déjà écrit un scraper en Node.js avec axios ou got brut, vous connaissez le scénario : 50 requêtes passent, puis soudain vous recevez des 403 Forbidden ou des challenges Cloudflare. Le problème n'est pas votre logique de scraping — c'est que votre client HTTP trahit son identité à plusieurs niveaux. got-scraping avec Node.js résout précisément cela en générant des ensembles d'en-têtes cohérents qui imitent un vrai navigateur, avec support HTTP/2 natif.

got-scraping est un wrapper construit par Apify au-dessus de got, le client HTTP populaire pour Node.js. Il intègre header-generator, une bibliothèque qui produit des en-têtes dans le bon ordre, avec les bonnes valeurs sec-ch-ua, accept-language, et tous les en-têtes que Chrome, Firefox ou Safari envoient réellement. Combiné à un got-scraping proxy résidentiel, vous obtenez un niveau de furtivité que axios.get() ne pourra jamais atteindre seul.

Avertissement légal : ce guide couvre la collecte de données publiques uniquement. Aux États-Unis, le CFAA criminalise l'accès non autorisé à des systèmes informatiques. En Europe, le RGPD régule le traitement des données personnelles. Respectez le robots.txt, les conditions d'utilisation des sites, et préférez toujours une API officielle quand elle existe.

Pourquoi les requêtes got/axios brutes se font repérer

Les systèmes anti-bot modernes comme Cloudflare, Datadome et PerimeterX ne se contentent plus de vérifier un seul signal. Ils croisent plusieurs couches :

  • Empreinte TLS (JA3/JA4) — la négociation TLS de Node.js diffère de celle de Chrome. Le JA3 fingerprint de Node 20 ne correspond à aucun navigateur connu.
  • Ordre des en-têtes — Chrome envoie toujours sec-ch-ua avant user-agent, puis accept. got et axios envoient les en-têtes dans l'ordre d'insertion, ce qui est immédiatement détectable.
  • En-têtes manquants — un vrai navigateur envoie 15–25 en-têtes, dont sec-fetch-dest, sec-fetch-mode, sec-fetch-site, priority. La plupart des clients HTTP n'en envoient que 4 ou 5.
  • HTTP/2 — Chrome utilise HTTP/2 par défaut avec HPACK et des paramètres SETTINGS spécifiques. Node.js en HTTP/1.1 se distingue immédiatement.

Le dépôt got-scraping d'Apify a été conçu spécifiquement pour résoudre ces problèmes. Il s'appuie sur header-generator pour produire des ensembles d'en-têtes cohérents — pas seulement un User-Agent aléatoire, mais toute la suite d'en-têtes que le navigateur choisi enverrait réellement, dans le bon ordre.

La surface idiomatique de got-scraping

got-scraping expose une API qui étend got de manière transparente. Vous pouvez l'utiliser comme un drop-in replacement, puis le configurer via got.extend().

got.extend, useHeaderGenerator et headerGeneratorOptions

Le pattern idiomatique consiste à créer une instance personnalisée avec got.extend(), en passant useHeaderGenerator: true et des headerGeneratorOptions qui contrôlent quels profils de navigateurs sont émis :

const { gotScraping } = require('got-scraping');

const client = gotScraping.extend({
  useHeaderGenerator: true,
  headerGeneratorOptions: {
    browsers: ['chrome', 'firefox'],
    devices: ['desktop'],
    operatingSystems: ['windows', 'macos'],
    locales: ['fr-FR', 'en-US'],
  },
  http2: true,
});

// Chaque requête reçoit un ensemble d'en-têtes cohérent
const res = await client.get('https://example.com');
console.log(res.headers);

Ici, got scraping header generator garantit que si le User-Agent dit Chrome 120 sur Windows, les en-têtes sec-ch-ua, sec-ch-ua-platform et accept seront cohérents avec cette signature. C'est cette cohérence qui manque à la plupart des scrapers DIY.

L'option proxyUrl pour HTTP/1 et HTTP/2

got-scraping accepte une option proxyUrl qui fonctionne aussi bien avec des proxies HTTP/1.1 qu'avec des proxies HTTP/2. Pour un nodejs scraping proxy résidentiel, vous passez simplement l'URL complète :

const res = await client.get('https://httpbin.org/headers', {
  proxyUrl: 'http://user-country-US-session-abc123:pass@gate.proxyhat.com:8080',
});

Le proxy résidentiel de ProxyHat supporte le tunneling HTTPS via CONNECT, ce qui signifie que votre trafic TLS reste chiffré de bout en bout — le proxy ne voit que la destination, pas le contenu.

Routage via proxies résidentiels ProxyHat

Une fois que vos en-têtes et votre empreinte TLS ressemblent à un vrai navigateur, la dernière couche de détection est l'adresse IP. Un datacenter IP (OVH, AWS, DigitalOcean) est immédiatement flagué par la plupart des bases de données IP reputation. C'est là que les proxies résidentiels deviennent essentiels.

Les proxies résidentiels de ProxyHat routent votre trafic via des adresses IP attribuées par des FAI réels (AT&T, Orange, Deutsche Telekom). Pour les sites anti-bot, votre requête ressemble à celle d'un utilisateur domestique normal, pas à celle d'un bot dans un datacenter.

ProxyHat HTTP sur le port 8080

Le endpoint HTTP par défaut est gate.proxyhat.com:8080. Le geo-targeting et les sessions sticky se configurent directement dans le nom d'utilisateur :

// Proxy résidentiel US avec session sticky
const proxyUrl = 'http://user-country-US-session-abc123:PASSWORD@gate.proxyhat.com:8080';

// Proxy résidentiel allemand ciblant Berlin
const proxyDe = 'http://user-country-DE-city-berlin-session-def456:PASSWORD@gate.proxyhat.com:8080';

SOCKS5 sur le port 1080

Pour les cas où SOCKS5 est préférable (par exemple, certains clients HTTP ne supportent que SOCKS5, ou vous voulez éviter le tunnel CONNECT), ProxyHat expose aussi SOCKS5 sur le port 1080 :

const proxySocks5 = 'socks5://user-country-GB-session-ghi789:PASSWORD@gate.proxyhat.com:1080';

Consultez la documentation ProxyHat pour la liste complète des paramètres de géo-ciblage disponibles.

Exemple Node.js complet : rotation de sessions résidentielles avec retry

Voici un exemple runnable qui combine got-scraping, la rotation de proxies résidentiels ProxyHat, et des hooks de retry. Le pattern clé : générer un identifiant de session unique par requête pour obtenir une nouvelle IP résidentielle à chaque appel.

const { gotScraping } = require('got-scraping');
const crypto = require('crypto');

const PROXYHAT_USER = 'user';
const PROXYHAT_PASS = 'pass';

function buildProxyUrl(country = 'US') {
  const session = crypto.randomBytes(8).toString('hex');
  return `http://${PROXYHAT_USER}-country-${country}-session-${session}:${PROXYHAT_PASS}@gate.proxyhat.com:8080`;
}

const client = gotScraping.extend({
  useHeaderGenerator: true,
  headerGeneratorOptions: {
    browsers: ['chrome'],
    devices: ['desktop'],
    operatingSystems: ['windows'],
    locales: ['en-US'],
  },
  http2: true,
  retry: {
    limit: 3,
    statusCodes: [403, 429, 500, 502, 503],
    backoffLimit: 5000,
  },
  hooks: {
    beforeRequest: [
      (options) => {
        // Nouvelle IP résidentielle à chaque requête
        options.proxyUrl = buildProxyUrl('US');
      },
    ],
    afterResponse: [
      (response, retryWithMergedOptions) => {
        if (response.statusCode === 403 || response.statusCode === 429) {
          // Rotation d'IP et retry
          return retryWithMergedOptions({
            proxyUrl: buildProxyUrl('US'),
          });
        }
        return response;
      },
    ],
  },
});

async function scrape(urls) {
  const results = [];
  for (const url of urls) {
    try {
      const res = await client.get(url, { timeout: { request: 15000 } });
      results.push({ url, status: res.statusCode, length: res.body.length });
    } catch (err) {
      results.push({ url, error: err.message });
    }
  }
  return results;
}

scrape([
  'https://httpbin.org/ip',
  'https://httpbin.org/headers',
  'https://httpbin.org/user-agent',
]).then(console.log);

Avec ce pattern, chaque requête obtient une IP résidentielle US différente. Si une IP se fait bloquer (403/429), le hook afterResponse déclenche un retry avec une nouvelle session — donc une nouvelle IP. Le retry.limit de 3 signifie jusqu'à 3 tentatives avec backoff exponentiel jusqu'à 5 secondes.

Patterns de production

Concurrency bornée avec p-limit

Scrapper 10 000 URLs en parallèle va saturer votre machine et probablement déclencher des rate limits côté serveur. Utilisez p-limit pour borner la concurrence :

const pLimit = require('p-limit');
const limit = pLimit(20); // 20 requêtes simultanées max

const tasks = urls.map((url) => limit(() => client.get(url)));
const results = await Promise.allSettled(tasks);

20 requêtes concurrentes est un bon point de départ. Au-delà, ajoutez un délai de 200–500ms entre les batches pour lisser la charge.

Certains sites nécessitent une session cookie cohérente à travers plusieurs pages. got-scraping supporte tough-cookie via l'option cookieJar :

const { CookieJar } = require('tough-cookie');
const jar = new CookieJar();

const sessionClient = client.extend({
  cookieJar: jar,
  hooks: {
    beforeRequest: [
      (options) => {
        options.proxyUrl = buildProxyUrl('US');
      },
    ],
  },
});

// La session cookie est maintenue à travers les requêtes
await sessionClient.get('https://example.com/login');
await sessionClient.get('https://example.com/dashboard');

Astuce : si vous voulez une session sticky (même IP + même cookies), gardez le même identifiant de session dans le nom d'utilisateur ProxyHat. Changez de session pour obtenir une nouvelle IP.

Passage à Crawlee et CheerioCrawler

Quand votre scraper grandit au-delà de quelques centaines d'URLs, il devient pertinent de passer à Crawlee, le framework d'Apify qui encapsule got-scraping. CheerioCrawler utilise got-scraping en interne et ajoute la gestion automatique des retries, du rate limiting, et du routing :

const { CheerioCrawler } = require('crawlee');

const crawler = new CheerioCrawler({
  requestHandler: async ({ $, request }) => {
    const title = $('title').text();
    console.log(request.url, title);
  },
  proxyConfiguration: {
    proxyUrls: [
      'http://user-country-US-session-s1:pass@gate.proxyhat.com:8080',
      'http://user-country-US-session-s2:pass@gate.proxyhat.com:8080',
      'http://user-country-US-session-s3:pass@gate.proxyhat.com:8080',
    ],
  },
  maxRequestsPerMinute: 60,
  autoscaledPoolOptions: { maxConcurrency: 20 },
});

await crawler.run(['https://example.com/page1', 'https://example.com/page2']);

Crawlee gère automatiquement le pool de proxies, le scaling, et les retries. C'est le chemin naturel quand got-scraping seul ne suffit plus.

Quand un navigateur headless devient inévitable

got-scraping est excellent pour le contenu HTML statique et les API JSON. Mais certains sites nécessitent une exécution JavaScript réelle : rendu SPA (React/Vue), challenges Cloudflare Turnstile, ou détéction active du canvas WebGL. Dans ces cas, passez à Playwright ou Puppeteer via Crawlee's PlaywrightCrawler. Le coût est réel : un navigateur headless consomme 150–300 MB de RAM par instance, contre ~2 MB pour got-scraping. Réservez cette approche pour les sites qui le justifient vraiment.

Approche Consommation RAM Vitesse Furtivité Cas d'usage
axios + proxy datacenter ~2 MB Très rapide Faible Sites sans protection
got-scraping + proxy résidentiel ~5 MB Rapide Élevée HTML statique, API JSON
Playwright + proxy résidentiel 150–300 MB Lent Très élevée SPA, challenges JS

Éthique et bonnes pratiques

  • Respectez robots.txt — vérifiez /robots.txt avant de scrapper. C'est une signal, pas une loi, mais l'ignorer vous expose à des risques.
  • Préférez les APIs officielles — si un site propose une API publique (même payante), c'est presque toujours plus fiable et plus rapide que le scraping.
  • Limitez votre taux — 1–5 requêtes/seconde par domaine est raisonnable. Au-delà, vous stresserez l'infrastructure cible.
  • Données publiques uniquement — ne contournez pas de paywalls, d'authentification, ou de restrictions d'accès. Le CFAA et le RGPD s'appliquent.
  • Identifiez-vous quand c'est approprié — pour la recherche académique ou le monitoring légitime, un User-Agent informatif peut être préférable à l'imitation.

Points clés à retenir

  • got-scraping avec Node.js génère des en-têtes de navigateur cohérents via header-generator, résolvant le problème de l'ordre et des en-têtes manquants.
  • Le support HTTP/2 natif réduit l'écart d'empreinte TLS entre votre client et un vrai navigateur Chrome.
  • Un got-scraping proxy résidentiel via gate.proxyhat.com:8080 est essentiel une fois les en-têtes couverts — les IP datacenter restent le signal le plus facile à détecter.
  • La rotation de sessions (identifiant unique par requête) donne une nouvelle IP résidentielle à chaque appel, avec retry automatique sur 403/429.
  • Bornez votre concurrence avec p-limit (20 concurrent max), utilisez des cookie jars pour les sessions persistantes, et passez à Crawlee pour le scraping à grande échelle.
  • Un navigateur headless (Playwright) n'est nécessaire que pour les SPA et les challenges JS actifs — le coût RAM est 30–60x supérieur.

Pour explorer les options de proxies résidentiels disponibles et leur tarification, consultez la page tarification ProxyHat. Pour voir la couverture géographique par pays et ville, visitez la page des locations ProxyHat. Des cas d'usage détaillés sont disponibles sur web scraping et SERP tracking.

Questions fréquentes

Qu'est-ce que got-scraping avec Node.js ?

got-scraping est un client HTTP pour Node.js développé par Apify, construit sur la bibliothèque got. Il intègre header-generator pour produire des en-têtes de navigateur cohérents (ordre, sec-ch-ua, accept-language) et supporte HTTP/2 natif. Contrairement à axios ou got brut, got-scraping génère automatiquement des ensembles d'en-têtes qui imitent un vrai navigateur Chrome, Firefox ou Safari, réduisant ainsi les risques de détection par les systèmes anti-bot.

Pourquoi got-scraping avec Node.js est-il important pour les utilisateurs de proxies ?

Les systèmes anti-bot modernes comme Cloudflare et Datadome croisent plusieurs signaux : empreinte TLS, ordre des en-têtes, en-têtes manquants et adresse IP. Même avec un proxy résidentiel, des en-têtes incohérents trahissent un bot. got-scraping résout la couche en-têtes et HTTP/2, tandis qu'un proxy résidentiel comme ProxyHat résout la couche IP. Combinés, ils offrent un niveau de furtivité qu'aucun des deux ne peut atteindre seul.

Quel type de proxy fonctionne le mieux avec got-scraping en Node.js ?

Les proxies résidentiels sont le meilleur choix pour got-scraping. Une fois que les en-têtes et l'empreinte TLS ressemblent à un vrai navigateur, l'adresse IP reste le signal le plus facile à détecter. Les IP datacenter (AWS, OVH, DigitalOcean) sont immédiatement flaguées par les bases de données de réputation IP. Les proxies résidentiels de ProxyHat routent le trafic via des IP attribuées par des FAI réels, rendant votre requête indiscernable de celle d'un utilisateur domestique normal.

Comment éviter les blocages en implémentant got-scraping avec Node.js ?

Pour éviter les blocages : utilisez header-generator avec des profils de navigateurs cohérents, routez chaque requête via un proxy résidentiel avec un identifiant de session unique pour obtenir une nouvelle IP à chaque appel, implémentez des hooks afterResponse pour retry automatique sur 403/429, bornez la concurrence avec p-limit (20 requêtes max), ajoutez des délais de 200-500ms entre les batches, et respectez le robots.txt ainsi que les limites de taux du site cible.

Prêt à commencer ?

Proxys résidentiels, ISP et mobiles dans plus de 148 pays. Créez un compte gratuit.

Créer un compte gratuit
← Retour au Blog