Podemos hacerlo, con Puppeteer, Vercel y café. Estaremos ejecutando una instancia de Chrome en una función serverless que se ejecuta en cada request qué hacemos, está potente, lo sé. Pero hagámoslo “por la anécdota” : ). Además así aprendemos juntos y aprovechamos a jugar un poco con las funciones serverless de Vercel.
Vercel , una compañia latinoamérica fundada por Guillermo Rauch. Es una plataforma de servicios serverless (similar a Netlify) muy, muy popular en el mundo dev ^^.
La imágen de cover(La misma del SEO) es la captura actual del ejemplo funcional
Primero, los recursos necesarios. Para hacer este proyecto necesitaremos:
Para instalarlo recomiendo usar NVM(Node Version Manager). Acá los scripts de instalación: https://github.com
Si instalamos una versión de Node mayor o igual a la 10.x vendrá npm por default, así que saltemos este paso
Si usas una versión menor a la 10.x lee un poco acá de cómo poder instalarlo: https://npmjs.com . psst, si usas una distro de ubuntu hace: sudo apt install npm
Crea tu cuenta en este link: https://vercel.com
npm i -g vercel
Okay, okay, ahora sí, veamos código.
Recuerdas lo que mencioné de que estaríamos instanciando Chrome dentro de una función serverless ?. Ahora te explicare un poco de porque es posible.
Google tiene un producto llamado Puppeteer, es un navegador headless que corre con Chromium. te da un montón de API’s para que podás controlarlo en NodeJs.
A pesar de ser “headless” ( Que corre sin UI ) necesitamos los binarios de dicho navegador para que funcione. Eso agrega peso a nuestro límite de 50MB permitido por las funciones lambda.
No solamente eso, un proyecto en Puppeteer con todas las dependencias pesaría más de 150MB, eso no lo hace posible para correr en una lambda. Bien, cómo lo solucionamos ? … Hay muchas versiones de “forks” de puppeteer para agregar a tus funciones y además para las distintas Clouds que existen (GCP, AWS, etc).
Para esta ocasión estaremos usando un módulo llamado “chrome-aws-lambda” y no usaremos la versión completa de puppeteer, más bien solamente su núcleo, con el paquete “puppeteer-core”
Creamos la carpeta en dónde vivirá nuestra app : )
mkdir puppeteer-vercel-cap && cd puppeteer-vercel-cap
npm init -y
Este comando iniciará un proyecto para usar npm y tomará la ruta dónde estemos para su configuración
sudo npm install --save chrome-aws-lambda
Instalamos chrome-aws-lambda
sudo npm install --save puppeteer-core
Instalamos puppeteer-core
vercel
En consola se mostrará un url, prueba si esta todo bien y continuemos.
mkdir api
La documentación de Vercel se dice que todas las rutas/archivos dentro de esta carpeta se servirán en nuestro website, por ejemplo el archivo api/hola.js
, estará disponible para nosotros en un url cómo: https://URL_BASE/api/hola
Para esta ocasión lo que haremos será nombrar nuestro archivo cómo index.js
así estará disponible cómo el índice en nuestra ruta /api
nano api/index.js
Ahora copiamos el código ejemplo para tomar la captura.
const chromium = require("chrome-aws-lambda")
const URL = `https://vercel.com/home`
const SEO_RESOLUTION = { width: 1200, height: 630 }
module.exports = async (req, res) => {
const browser = await chromium.puppeteer.launch({
args: [...chromium.args, "--hide-scrollbars", "--disable-web-security"],
defaultViewport: chromium.defaultViewport,
executablePath: await chromium.executablePath,
headless: true,
ignoreHTTPSErrors: true,
})
const page = await browser.newPage()
page.setViewport(SEO_RESOLUTION)
await page.goto(URL, { waitUntil: "networkidle0" })
const screenShotBuffer = await page.screenshot()
res.writeHead(200, {
"Content-Type": "image/png",
"Content-Length": Buffer.byteLength(screenShotBuffer),
})
res.end(screenShotBuffer)
}
CTRL + SHIFT + v
CTRL + o
, luego ENTER
y por último para salir CTRL + x
cat api/index.js
Por cierto, en este caso cómo ejemplo tomaremos la captura al home de Vercel: https://vercel.com . Puedes cambiarlo si gustas : ).
vercel dev
Esto iniciará un server en tu PC en el puerto 3000. Para ver si todo anda bien xD, puedes testear acá: http://localhost:3000/api
vercel --prod
Esto iniciará el proceso para crear una URL pública para compartir con tus amigos del proyecto : ‘ )
Eso es todo amigos, muchas gracias por tu lectura ^^ . Te pido compartas esto con tus conocidos si te gustó y si no te gustó, también, así los molestas : )
Por cierto este ejemplo abre la ventana a muchaaas cosas. Reportes, imágenes que se actualizan en cada fetch ( cómo los trucos en github y perfiles con data que casi son dashboards ). Creación de imágenes con datos personalizables, tests serverless de UI, scrappers, etc, etc, etc.
Ejemplo funcional: https://puppeteer-vercel-screenshot.vercel.app
Ver el código del proyecto en Github
PD: El código en Github está un poco más “documentado”, 😁