Node.js, Tor, Titiritero y Cheerio: raspado web anónimo

El raspado web es un método de recopilación de datos de sitios web. Este término se usa comúnmente en relación con la recopilación automatizada de datos. Hoy hablaremos sobre cómo recopilar datos de sitios de forma anónima. La razón por la cual alguien puede desear el anonimato en el raspado web es porque muchos servidores web aplican ciertas reglas a las conexiones desde direcciones IP, desde las cuales se realiza un cierto número de solicitudes durante un cierto período de tiempo. Aquí usaremos las siguientes herramientas:

  • Titiritero : para acceder a páginas web.
  • Cheerio : para analizar el código HTML.
  • Tor : para ejecutar cada solicitud desde una dirección IP diferente.

Cabe señalar que los aspectos legales del raspado web son un tema complejo y a menudo poco claro. Por lo tanto, respete los " Términos de uso " de las páginas cuyos datos recopila. Aquí hay un buen material sobre este tema.



Instalación Tor


Comencemos desde el principio; por lo tanto, antes que nada, instale el cliente Tor usando el siguiente comando:

sudo apt-get install tor

Configuración Tor


Ahora configure el cliente Tor. La configuración predeterminada de Tor usa el puerto SOCKS , que nos da una ruta a un solo nodo de salida (es decir, una dirección IP). Para el uso diario de Tor, como simplemente navegar por la web, este es un buen ajuste. Pero necesitamos algunas direcciones IP. Esto le permitirá cambiar entre ellos durante el proceso de raspado web.

Para configurar Tor como lo necesitamos, simplemente abrimos puertos adicionales para escuchar conexiones SOCKS. Esto se hace agregando varias entradas SocksPortal archivo de configuración principal del programa, que se puede encontrar en /etc/tor.

Abra el archivo /etc/tor/torrccon algún editor de texto y agregue las siguientes entradas al final del archivo:

#  4 SOCKS-,       Tor-.

SocksPort 9050
SocksPort 9052
SocksPort 9053
SocksPort 9054

Aquí vale la pena prestar atención a lo siguiente:

  • SocksPort . — , , SOCKS, .
  • SocksPort , , , - .
  • 9050 — , Tor- .
  • 9051. Tor , , , Tor.
  • 9051, , 1.

Para aplicar los cambios realizados en el archivo de configuración, reinicie el cliente Tor:

sudo /etc/init.d/tor restart

Crear un nuevo proyecto Node.js


Cree un nuevo directorio para el proyecto. Vamos a la llaman superWebScraping:

mkdir superWebScraping

Vayamos a este directorio e inicialicemos un proyecto de Nodo vacío:

cd superWebScraping && npm init -y

Establezca las dependencias necesarias:

npm i --save puppeteer cheerio

Trabaja con sitios web usando Puppeteer


Puppeteer es un navegador sin una interfaz de usuario que utiliza el protocolo DevTools para interactuar con Chrome o Chromium . La razón por la que no usamos la biblioteca aquí para trabajar con solicitudes, como tor-request , es porque dicha biblioteca no podrá procesar sitios creados como aplicaciones web de una sola página cuyos contenidos se cargan dinámicamente.

Cree un archivo index.jsy coloque el siguiente código en él. Las características principales de este código se describen en los comentarios.

/**
 *   puppeteer.
 */
const puppeteer = require('puppeteer');

/**
 *   main  , 
 *     -.
 * ,      ,
 *   ,     
 *  puppeteer.
 */
async function main() {
  /**
   *  Chromium.   `headless`   false,
   *     .
   */
  const browser = await puppeteer.launch({
    headless: false
  });

  /**
   *   .
   */
  const page = await browser.newPage();

  /**
   *   ,   https://api.ipify.org.
   */
  await page.goto('https://api.ipify.org');

  /**
   *  3     .
   */
  setTimeout(() => {
    browser.close();
  }, 3000);
}

/**
 *  ,  main().
 */
main();

Ejecute el script con el siguiente comando:

node index.js

Después de eso, la ventana del navegador Chromium debería aparecer en la pantalla, en la que la dirección está abierta https://api.ipify.org.


Ventana del navegador, no se utiliza la conexión Tor.

La abrí en la ventana del navegador precisamentehttps://api.ipify.orgporque esta página puede mostrar la dirección IP pública desde la que se accede. Esta es la dirección que es visible para los sitios que visito si los visito sin usar Tor.

Cambie el código anterior agregando la siguiente clave al objeto con los parámetros que se pasanpuppeteer.launch:

  /**
   *  Chromium.   `headless`  false,
   *     .
   */
  const browser = await puppeteer.launch({
  headless: false,
  
  //   .
  args: ['--proxy-server=socks5://127.0.0.1:9050']
});

Pasamos una discusión al navegador --proxy-server. El valor de este argumento le dice al navegador que debe usar un servidor proxy socks5 que se ejecute en nuestra computadora y accesible en el puerto 9050. El número de puerto es uno de esos números que ingresamos previamente en el archivo torrc.

Ejecute el script nuevamente:

node index.js

Esta vez, en la página abierta, puede ver una dirección IP diferente. Esta es la dirección utilizada para ver el sitio a través de la red Tor.


Ventana del navegador, se utiliza la conexión Tor.

En mi caso, apareció una dirección en esta ventana144.217.7.33. Es posible que tenga alguna otra dirección. Tenga en cuenta que si vuelve a ejecutar el script y utiliza el mismo número de puerto (9050), recibirá la misma dirección IP que recibió anteriormente.


Relanzada la ventana del navegador, se utiliza la conexión Tor.

Es por eso que en la configuración de Tor abrimos varios puertos. Intente conectar su navegador a un puerto diferente. Esto cambiará la dirección IP.

Recolección de datos con Cheerio


Ahora que tenemos un mecanismo conveniente para cargar páginas, es hora de hacer scraping web. Para esto, vamos a utilizar la biblioteca cheerio . Este es un analizador HTML cuya API está construida de la misma manera que la API jQuery . Nuestro objetivo es obtener 5 de las últimas publicaciones de la página de Hacker News.

Vaya al sitio web de Hacker News .


Sitio web de Hacker News

Queremos tomar 5 titulares nuevos de la página abierta (ahora es HAKMEM (1972), Larry Roberts ha muerto y otros). Al examinar el título del artículo utilizando las herramientas de desarrollo del navegador, noté que cada título se coloca en un elemento HTML<a>con una clasestorylink.


Examen de la estructura del documento

Para extraer del código HTML de la página lo que necesitamos, debemos realizar la siguiente secuencia de acciones:

  • Iniciar una nueva instancia de navegador sin una interfaz de usuario conectada al proxy Tor.
  • Crea una nueva página.
  • Ve a la dirección https://news.ycombinator.com/.
  • Recuperando el contenido HTML de la página.
  • Cargando el contenido HTML de la página en cheerio.
  • Crear una matriz para guardar títulos de artículos.
  • Acceso a elementos con una clase storylink.
  • Obteniendo los primeros 5 elementos usando el método cheerio slice () .
  • Elemento de derivación obtenido usando el método cheerio each () .
  • Escriba cada encabezado encontrado en una matriz.

Aquí está el código que implementa estas acciones:

const puppeteer = require('puppeteer');

/**
 *   cheerio.
 */
const cheerio = require('cheerio');

async function main() {
  const browser = await puppeteer.launch({
    /**
     *       (   ).
     */
    headless: true,
    args: ['--proxy-server=socks5://127.0.0.1:9050']
  });

  const page = await browser.newPage();

  await page.goto('https://news.ycombinator.com/');

  /**
   *      HTML-.
   */
  const content = await page.content();

  /**
   *    cheerio.
   */
  const $ = cheerio.load(content);


  /**
   *      .
   */
  const titles = [];

  /**
   *   ,   `storylink`.
   *  slice()      5   .
   *      each().
   */
  $('.storylink').slice(0, 5).each((idx, elem) => {
    /**
     *   HTML-,   .
     */
    const title = $(elem).text();
  
    /**
     *    .
     */
    titles.push(title);
  })

  browser.close();
  
  /**
   *     .
   */
  console.log(titles);
}

main();

Esto es lo que sucede después de ejecutar este script.


Primeros 5 titulares de noticias de hackers extraídos con éxito del código de la página

Raspado continuo utilizando diferentes direcciones IP


Ahora hablemos sobre cómo usar los diversos puertos SOCKS que especificamos en el archivo torrc. Es bastante simple Declararemos una matriz, cada una de las cuales contendrá un número de puerto. Luego cambie el nombre de la función main()a una función scrape()y declare una nueva función main()que llame a la función scrape(), pasándole un nuevo número de puerto con cada llamada.

Aquí está el código terminado:

const puppeteer = require('puppeteer');
const cheerio = require('cheerio');

async function scrape(port) {
  const browser = await puppeteer.launch({
    args: ['--proxy-server=socks5://127.0.0.1:' + port]
  });

  const page = await browser.newPage();
  await page.goto('https://news.ycombinator.com/');
  const content = await page.content();

  const $ = cheerio.load(content);

  const titles = [];

  $('.storylink').slice(0, 5).each((idx, elem) => {
    const title = $(elem).text();
    titles.push(title);
  });

  browser.close();
  return titles;
}

async function main() {
  /**
   *  SOCKS- Tor,    torrc. 
   */
  const ports = [
    '9050',
    '9052',
    '9053',
    '9054'
  ];
  
  /**
   *  -...
   */
  while (true) {
    for (const port of ports) {
      /**
       * ...  -    .
       */
      console.log(await scrape(port));
    }
  }
}

main();

Resumen


Ahora tiene herramientas a su disposición que le permiten hacer un raspado web anónimo.

¡Queridos lectores! ¿Alguna vez has hecho web scraping? Si es así, díganos qué herramientas utiliza para esto.

Source: https://habr.com/ru/post/undefined/


All Articles