Comment utiliser un proxy avec Node Fetch et construire un scraper web
Mihnea-Octavian Manolache le 24 avril 2023

Tout d'abord, lors de la construction d'un scraper web, les proxies sont certainement très importants. Ensuite, node-fetch est l'un des clients HTTP JavaScript les plus populaires. Il est donc logique de combiner les deux et de créer un scraper web.
C'est pourquoi aujourd'hui nous allons discuter de l'utilisation d'un proxy avec node-fetch. Et en bonus, nous allons construire un scraper web à partir de cette infrastructure.
Ainsi, à la fin de cet article :
- Vous aurez une bonne compréhension du fonctionnement des proxys dans le cadre du web scraping.
- Vous apprendrez à intégrer un proxy avec node-fetch
- Un projet sera ajouté à votre portfolio personnel.
Qu'est-ce qu'un proxy et pourquoi l'utiliser pour le web scraping ?
Dans les réseaux informatiques, les proxys agissent comme des "middlewares" entre un client et un serveur. L'architecture d'un serveur proxy est assez complexe, mais à un niveau élevé, voici ce qui se passe lorsque vous utilisez un proxy :
- Vous "tapez" dans le serveur proxy et spécifiez la destination (serveur) que vous essayez d'atteindre (scrape).
- Le serveur proxy se connecte à votre cible et récupère les résultats (les fichiers HTML d'un site web par exemple).
- Le serveur proxy vous renvoie alors la réponse qu'il a reçue du serveur de destination

Dans cette chaîne, votre IP reste cachée au serveur de destination, car vous ne vous y connectez jamais. C'est la raison principale pour laquelle les proxys jouent un rôle si important dans le web scraping. Ils "cachent" l'adresse IP du web scraper, de sorte qu'elle ne sera pas bloquée par les systèmes antibots.
Pourquoi utiliser node-fetch pour le web scraping ?
Si JavaScript est votre langage de programmation préféré, il existe de nombreux clients HTTP que vous pouvez utiliser pour construire un scraper web. Parmi les plus populaires, il y a axios, got et quelques autres listés ici. Mais node-fetch reste l'un des paquets npm les plus téléchargés, et il y a une raison à cela.
Tout d'abord, il s'agit du premier package à implémenter l'API Fetch dans Node JS. Ensuite, à partir de la version 17.5.0, l'équipe Node JS a ajouté l'API Fetch, afin qu'elle ne soit pas nécessaire en tant que dépendance tierce. Aujourd'hui encore, dans la version 19.3.0 de Node JS, fetch est toujours considéré comme expérimental. node-fetch reste donc la solution la plus stable.
Spécifique au scraping, node-fetch est un outil formidable car, comme son nom l'indique, il est utilisé pour récupérer des ressources à partir de différentes sources. Et c'est peut-être la définition la plus élémentaire du scraping.
Comment utiliser node-fetch avec des proxies ?
Pour faire court, il n'y a pas de méthode intégrée pour utiliser un proxy avec node-fetch. Donc, si vous voulez construire un scraper web, mais que votre infrastructure repose sur node-fetch, vous risquez d'exposer votre véritable IP. Cela signifie que vous risquez d'être bloqué par un logiciel anti-bot.
Heureusement, il existe des solutions de contournement. L'une d'entre elles nous est offerte par Nathan Rajlich, qui a construit un module qui implémente http.Agent et qui s'appelle https-proxy-agent. L'installation est disponible via npm. De plus, l'implémenter avec node-fetch est assez simple :
import fetch from 'node-fetch';
import HttpsProxyAgent from "https-proxy-agent";
const fetch_proxy = async () => {
const proxy = new HttpsProxyAgent('http://1.255.134.136:3128');
const response = await fetch('https://httpbin.org/ip', { agent: proxy});
const data = await response.text();
console.log(data);
}
fetch_proxy()
Pour les besoins de ce test, j'ai utilisé un proxy gratuit de Proxy Scrape. Comme prévu, la réponse indique que la demande provient de l'IP du proxy et non de mon IP locale :
"origin" : "1.255.134.136"
Une autre option consiste à utiliser node-fetch-with-proxy. Ce paquetage utilise proxy-agent comme une dépendance à part entière de node-fetch. Pour que cela fonctionne, tout ce que vous avez à faire est de définir la variable d'environnement 'HTTP_PROXY'. Elle prend l'adresse IP et le numéro de port de votre serveur proxy comme valeur. Vous pouvez alors utiliser la syntaxe habituelle de node-fetch pour effectuer vos appels, qui seront automatiquement routés vers le serveur proxy. Voici un exemple :
import fetch from "node-fetch-with-proxy" ;
fetch('http://httpbin.org/ip')
.then(res => res.json())
.then(json => console.log(json)) ;
Comment construire un scraper web en utilisant un proxy avec node-fetch ?
Enfin, nous avons déjà construit un scraper web. Les exemples de code ci-dessus font exactement ce que fait tout scrapeur web, à savoir collecter des données à partir d'un site web. Cependant, dans un scénario réel, un scraper web est un peu plus complexe. Par exemple, les données brutes doivent être traitées, ou nous devons vérifier et analyser les en-têtes ou les cookies collectés. Plongeons donc un peu plus profondément et transformons notre premier échantillon en un véritable scraper. Fixons quelques attentes :
- Nous devrions être en mesure de renvoyer le code HTML brut
- Nous devrions pouvoir renvoyer l'intégralité de la réponse sous la forme d'un objet JSON.
- Nous devrions être en mesure d'extraire des éléments sur la base de sélecteurs spécifiques.
En supposant que vous ayez déjà installé node-fetch et https-proxy-agent, nous avons besoin d'une dernière chose : un analyseur HTML. Je choisis toujours cheerio pour le web scraping. Assurez-vous donc de l'installer dans votre projet. Ceci étant dit, commençons :
#1 : Importer des dépendances
La première chose à faire est d'importer les paquets dont nous avons parlé plus haut. Je pense que cette partie ne nécessite pas d'explication supplémentaire :
import fetch from 'node-fetch' ;
import HttpsProxyAgent from "https-proxy-agent" ;
import * as cheerio from 'cheerio' ;
#2 : Logique de raclage
Nous avons besoin que notre scraper soit capable d'effectuer trois actions : retourner le HTML de la ligne, retourner la réponse entière, et retourner un élément basé sur son sélecteur CSS. L'une d'entre elles a déjà été partiellement implémentée auparavant. Mais séparons tout en trois fonctions :
const raw_html = async (proxyServer, targetURL) => {
const proxy = new HttpsProxyAgent(proxyServer);
const response = await fetch(targetURL, { agent: proxy});
const data = await response.text();
return data;
}
const json_response = async (proxyServer, targetURL) => {
const proxy = new HttpsProxyAgent(proxyServer);
const response = await fetch(targetURL, { agent: proxy});
const data = {
url: response.url,
status: response.status,
Headers: response.headers,
body: await response.text()
}
return data;
}
const select_css = async (proxyServer, targetURL, cssSelector) => {
const proxy = new HttpsProxyAgent(proxyServer);
const response = await fetch(targetURL, { agent: proxy});
const html = await response.text();
const $ = cheerio.load(html);
return $(cssSelector).text();
}
#3 : Analyseur d'arguments
Nous pouvons utiliser les arguments terminaux pour distinguer les trois options que nous avons implémentées dans notre scraper. Il y a des options que vous pouvez utiliser pour analyser les arguments terminaux dans Node, mais j'aime garder les choses simples. C'est pourquoi nous utiliserons process.argv, qui génère un tableau d'arguments. Notez que les deux premiers éléments de ce tableau sont 'node' et le nom de votre script. Par exemple, si vous lancez `node scraper.js raw_html`, le tableau d'arguments ressemblera à ceci :
[
'/usr/local/bin/node',
'path_to_directory/scraper.js',
'raw_html'
]
En ignorant les deux premiers éléments, nous utiliserons la logique suivante :
- le premier argument indiquera la fonction que nous voulons exécuter ;
- le second pointera vers notre cible (le site web que nous voulons récupérer) ;
- le troisième pointera vers le serveur proxy ;
- et un quatrième pointera vers le sélecteur css.
Ainsi, la commande pour lancer notre scraper devrait ressembler à ceci :
~ " node scraper.js raw_html https://webscrapingapi.com http://1.255.134.136:3128
Cela se traduit simplement par l'extraction du html brut de la page d'accueil de WebScrapingAPI et l'utilisation de http://1.255.134.136 en tant que middleware proxy. La dernière étape consiste à coder la logique de ces arguments, de manière à ce que notre code comprenne la commande run :
const ACTION = process.argv[2]
const TARGET = process.argv[3]
const PROXY = process.argv[4]
const SELECTOR = process.argv[5]
switch (ACTION) {
case 'raw_html':
console.log(await raw_html(PROXY, TARGET))
break
case 'json_response':
console.log(await json_response(PROXY, TARGET))
break
case 'select_css':
SELECTOR ? console.log(await select_css(PROXY, TARGET, SELECTOR)) : console.log('Please specify a CSS selector!')
break
default:
conssole.log('Please choose between `raw_html`, `json_response` and `select_css`')
}
Et c'est à peu près tout. Nous vous félicitons ! Vous avez réussi à créer un scraper web entièrement fonctionnel en utilisant un proxy avec node-fetch. Je vous mets maintenant au défi d'ajouter d'autres fonctionnalités à ce scraper, de créer votre propre version et de l'utiliser comme atout dans votre portefeuille personnel.
L'utilisation d'un proxy avec node-fetch peut ne pas être suffisante pour le web scraping
Comme j'aime à le dire, le scraping furtif ne se limite pas à cacher son adresse IP. En réalité, l'utilisation d'un serveur proxy pour votre scraper web n'est qu'une couche de protection contre les logiciels anti-bots. Une autre couche consiste à modifier votre agent utilisateur en [ajoutant des en-têtes personnalisés à votre requête] (LIEN https://trello.com/c/n8xZswSI/14-2-8-january-article-13-http-headers-with-axios).
Chez Web Scraping API par exemple, nous avons une équipe dédiée qui travaille sur des techniques d'évasion personnalisées. Certaines d'entre elles vont jusqu'à modifier les valeurs par défaut du navigateur sans tête afin d'éviter le fingerprinting.
De plus, comme les sites modernes rendent le contenu de manière dynamique à l'aide de JavaScript, un simple client HTTP tel que node-fetch peut ne pas suffire. Vous voudrez peut-être explorer l'utilisation d'un véritable navigateur web. Python's selenium ou Node's puppeteer sont deux options que vous pouvez envisager à cet égard.
Conclusions
L'utilisation d'un proxy avec node-fetch est un excellent point de départ pour construire un scraper web. Cependant, vous devez tenir compte du fait que les deux ne sont pas "directement compatibles" et que vous devrez utiliser une solution tierce pour les relier. Heureusement, les possibilités sont nombreuses et la communauté JavaScript est toujours heureuse d'aider les nouveaux venus.
Construire un scraper furtif est cependant plus difficile et vous devrez trouver des techniques d'évasion plus complexes. Mais j'aime voir une opportunité dans chaque chose. Pourquoi ne pas prendre ce que vous avez appris aujourd'hui et le compléter ? Avec un peu de chance, à la fin, vous aurez le meilleur scraper web écrit avec node-fetch et des proxies. Comme toujours, mon conseil est de continuer à apprendre !
Nouvelles et mises à jour
Restez au courant des derniers guides et nouvelles sur le web scraping en vous inscrivant à notre lettre d'information.
We care about the protection of your data. Read our <l>Privacy Policy</l>.Privacy Policy.

Articles connexes

Apprenez quel est le meilleur navigateur pour contourner les systèmes de détection de Cloudflare lorsque vous faites du web scraping avec Selenium.


Découvrez 3 façons de télécharger des fichiers avec Puppeteer et construisez un scraper web qui fait exactement cela.


Apprenez à extraire les avis de Google Maps avec notre API à l'aide de Node.js. Obtenez des instructions pas à pas sur la configuration, l'extraction des données et la résolution des problèmes potentiels.
