Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
WorkerConf 2021 - Browser automation with Puppe...
Search
Sponsored
·
Your Podcast. Everywhere. Effortlessly.
Share. Educate. Inspire. Entertain. You do you. We'll handle the rest.
→
Jecelyn Yeen
June 25, 2021
Programming
1.9k
0
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
WorkerConf 2021 - Browser automation with Puppeteer
Jecelyn Yeen
June 25, 2021
More Decks by Jecelyn Yeen
See All by Jecelyn Yeen
My Journey as Technical Presenter
jecfish
0
1k
Becoming a GDE
jecfish
0
4k
How to get started in IT Freelancing
jecfish
1
300
New Web API & Stylings
jecfish
3
770
如何打造高性能且SEO友好的单页应用(SPA)
jecfish
2
940
JS SEO
jecfish
4
1.6k
Web Performance Optimization
jecfish
5
1.8k
Have Fun with Angular
jecfish
0
130
RxJs Trex
jecfish
0
730
Other Decks in Programming
See All in Programming
カツオ、ご期待ください
suneo3476
0
150
Ghostty + Neovimで作る 透明でカッコ良い開発環境
j341nono
0
150
ジョジョの世界をXRで再現する
mofurune
0
130
RAG の “R” を Swift で覗いてみる 〜「意味から探す」検索の仕組み〜
nao_randd
0
120
Streamlitで実現する自然言語データアプリ開発
ayumu_yamaguchi
1
340
mrbgem 三角測量 開発
ogom
0
200
The Rails Doctrine Decade
koic
2
500
Workers Cache を知る
syumai
0
340
[ハンズオン]AIへの指示だけで「五目並べ」を作ってみよう
satoshi256kbyte
1
350
re:Inventに行く前に知っておきたい現地参加のノウハウ
nokomoro3
0
370
仕様駆動開発による爆速プロダクト開発 / Bakusoku Spec Driven Development
kobakei
0
200
20260914 AIエージェント時代のPlatform Engineering LLM基盤とプロダクトの責務境界線
kanfab1
7
2.4k
Featured
See All Featured
[SF Ruby Conf 2025] Rails X
palkan
3
1.4k
Code Review Best Practice
trishagee
74
20k
How to Align SEO within the Product Triangle To Get Buy-In & Support - #RIMC
aleyda
2
1.8k
Noah Learner - AI + Me: how we built a GSC Bulk Export data pipeline
techseoconnect
PRO
0
450
Code Reviewing Like a Champion
maltzj
528
40k
The SEO Collaboration Effect
kristinabergwall1
1
590
Discover your Explorer Soul
emna__ayadi
2
1.3k
Redefining SEO in the New Era of Traffic Generation
szymonslowik
1
460
Stop Working from a Prison Cell
hatefulcrawdad
274
21k
Git: the NoSQL Database
bkeepers
PRO
433
67k
The Organizational Zoo: Understanding Human Behavior Agility Through Metaphoric Constructive Conversations (based on the works of Arthur Shelley, Ph.D)
kimpetersen
PRO
0
490
Navigating the moral maze — ethical principles for Al-driven product design
skipperchong
2
600
Transcript
@JecelynYeen Developer advocate, Google @ChromeDevTools
None
My road bike
Mountain bike My road bike
Mountain bike Hiking, hot and humid My road bike
Mountain bike Hiking, hot and humid Hiking, Switzerland My road
bike
None
Browser automation with Puppeteer
PM YANG Professional developer PAUL
PM YANG I want a daily email on our server’s
internet speed. Professional developer PAUL
PM YANG I want a daily email on our server’s
internet speed. Professional developer PAUL Why does he need that?
PM YANG It’s easy. Go to fast.com on the server
and send me the screenshot.
PM YANG It’s easy. Go to fast.com on the server
and send me the screenshot. Professional developer PAUL I never said it’s hard...
None
None
Professional developer PAUL There are 2 ways to do this:
Manually 1. Login to server 2. Open a browser 3. Go to fast.com 4. Take a screenshot 5. Send email
Professional developer PAUL There are 2 ways to do this:
Manually 1. Login to server 2. Open a browser 3. Go to fast.com 4. Take a screenshot 5. Send email Automate it 1. Schedule a daily server task 2. Automate screenshot 3. Automate email sending
Professional developer PAUL Researching...
Professional developer PAUL Researching... Puppeteer
None
Browser automation library for Node.js
Control a browser with modern JavaScript API.
const puppeteer = require('puppeteer'); (async () => { })();
const puppeteer = require('puppeteer'); (async () => { const browser
= await puppeteer.launch(); })();
const puppeteer = require('puppeteer'); (async () => { const browser
= await puppeteer.launch(); const page = await browser.newPage(); })();
const puppeteer = require('puppeteer'); (async () => { const browser
= await puppeteer.launch(); const page = await browser.newPage(); await page.goto('https://fast.com/'); })();
const puppeteer = require('puppeteer'); (async () => { const browser
= await puppeteer.launch(); const page = await browser.newPage(); await page.goto('https://fast.com/'); await page.screenshot({ path: 'img/screenshot-yyyyMMdd.png' }); })();
const puppeteer = require('puppeteer'); (async () => { const browser
= await puppeteer.launch(); const page = await browser.newPage(); await page.goto('https://fast.com/'); await page.screenshot({ path: 'img/screenshot-yyyyMMdd.png' }); await browser.close(); })();
Not working
None
const puppeteer = require('puppeteer'); (async () => { const browser
= await puppeteer.launch(); const page = await browser.newPage(); await page.goto('https://fast.com/'); await page.waitForSelector('.speed-results-container.succeeded'); await page.screenshot({ path: 'img/screenshot-yyyyMMdd.png' }); await browser.close(); })();
Run it again
Professional developer PAUL
PM YANG Cool, it will be great if to have
date in the screenshot. Possible?
const puppeteer = require('puppeteer'); (async () => { const browser
= await puppeteer.launch(); const page = await browser.newPage(); await page.goto('https://fast.com/'); await page.waitForSelector('.speed-results-container.succeeded'); await page.$eval('#your-speed-message', (el, dt) => { el.innerText = `Internet speed as of ${dt} is`; }, 'yyyy-MM-dd')); await page.screenshot({ path: `img/screenshot-yyyyMMdd.png` }); await browser.close(); })();
PM YANG I want...
// Save as pdf, only work in headless mode await
page.pdf({ path: `doc/speed-yyyyMMdd.pdf` }); // Click to show more details await page.click('#show-more-details-link'); await page.waitForSelector('#upload-label.succeeded', { timeout: 0 }); // Emulate mobile view and save screenshot // src/common/DeviceDescriptors.ts const tablet = puppeteer.devices['iPad Mini']; await page.emulate(tablet); await page.screenshot({ path: `img/screenshot-yyyyMMdd.png` }); // Reload page await page.reload();
// Save as pdf, only work in headless mode await
page.pdf({ path: `doc/speed-yyyyMMdd.pdf` }); // Click to show more details await page.click('#show-more-details-link'); await page.waitForSelector('#upload-label.succeeded', { timeout: 0 }); // Emulate mobile view and save screenshot // src/common/DeviceDescriptors.ts const tablet = puppeteer.devices['iPad Mini']; await page.emulate(tablet); await page.screenshot({ path: `img/screenshot-yyyyMMdd.png` }); // Reload page await page.reload();
// Save as pdf, only work in headless mode await
page.pdf({ path: `doc/speed-yyyyMMdd.pdf` }); // Click to show more details await page.click('#show-more-details-link'); await page.waitForSelector('#upload-label.succeeded', { timeout: 0 }); // Emulate mobile view and save screenshot // src/common/DeviceDescriptors.ts const tablet = puppeteer.devices['iPad Mini']; await page.emulate(tablet); await page.screenshot({ path: `img/screenshot-yyyyMMdd.png` }); // Reload page await page.reload();
// Save as pdf, only work in headless mode await
page.pdf({ path: `doc/speed-yyyyMMdd.pdf` }); // Click to show more details await page.click('#show-more-details-link'); await page.waitForSelector('#upload-label.succeeded', { timeout: 0 }); // Emulate mobile view and save screenshot // src/common/DeviceDescriptors.ts const tablet = puppeteer.devices['iPad Mini']; await page.emulate(tablet); await page.screenshot({ path: `img/screenshot-yyyyMMdd.png` }); // Reload page await page.reload();
github.com/puppeteer
❤
const browser = await puppeteer.launch(); const page = await browser.newPage();
await page.goto('https://v8.dev/blog/10-years'); // Create screenshots of your web app in Light Mode and Dark Mode. // Tip: check out `npx dark-mode-screenshot` for more options! await page.emulateMediaFeatures([{ name: 'prefers-color-scheme', value: 'light' }]); await page.screenshot({ path: 'light.png', fullPage: true }); await page.emulateMediaFeatures([{ name: 'prefers-color-scheme', value: 'dark' }]); await page.screenshot({ path: 'dark.png', fullPage: true }); await browser.close();
const browser = await puppeteer.launch(); const page = await browser.newPage();
await page.goto('https://mathiasbynens.be/demo/timezone'); page.evaluate(() => { globalThis.date = new Date(1479579154987); }); await page.emulateTimezone('America/Buenos_Aires'); console.log(await page.evaluate(() => date.toString())); // → 'Sat Nov 19 2016 15:12:34 GMT-0300 (Argentina Standard Time)' await page.emulateTimezone('Asia/Kuala_Lumpur'); console.log(await page.evaluate(() => date.toString())); // → 'Sun Nov 20 2016 02:12:34 GMT+0800 (Malaysia Time)' await browser.close();
const browser = await puppeteer.launch(); const page = await browser.newPage();
await page.goto('https://developer.chrome.com/tags/devtools/'); await page.emulateVisionDeficiency('blurredVision'); await page.screenshot({ path: 'blurred-vision.png', fullPage: true }); await page.emulateVisionDeficiency('achromatopsia'); await page.screenshot({ path: 'achromatopsia.png', fullPage: true }); await page.emulateVisionDeficiency('deuteranopia'); await page.screenshot({ path: 'deuteranopia.png', fullPage: true }); await browser.close();
addyosmani.com/blog/ puppeteer-recipes/
const browser = await puppeteer.launch();
const browser = await puppeteer.launch(); // Launch options const browser
= await puppeteer.launch({ product: 'firefox' });
const browser = await puppeteer.launch(); // Launch options const browser
= await puppeteer.launch({ product: 'firefox' }); const browser = await puppeteer.launch({ headless: false, slowMo: 3000 });
const browser = await puppeteer.launch(); // Launch options const browser
= await puppeteer.launch({ product: 'firefox' }); const browser = await puppeteer.launch({ headless: false, slowMo: 3000 }); const browser = await puppeteer.launch({ devtools: true });
goo.gle/devtools-blog
@JecelynYeen Developer advocate, Google @ChromeDevTools