Mục lục
1. Pupperteer là gì?
Nguyên văn
Puppeteer is a Node library which provides a high-level API to control headless Chrome or Chromium over the DevTools Protocol. It can also be configured to use full (non-headless) Chrome or Chromium.
Tạm dịch là:
Puppeteer là một thư viện của Node cung cấp API cấp cao để kiểm soát Chrome hoặc Chromium sử dụng giao thức DevTools. Puppeteer mặc định chạy headless, nhưng có thể được định cấu hình để chạy non-headless.
Mình sẽ giải thích một chút: Theo mình hiểu, run headless là việc bạn chạy browser mà không có giao diện. Việc chạy browser như vậy thường để crawl dữ liệu, chụp ảnh màn hình,… chứ không phải để duyệt web.
Một số việc khá hay ho mà bạn có thể làm với Pupperteer là:
- Chụp ảnh màn hình hoặc xuất file pdf của các trang.
- Crawl một SPA (Single-Page Application) và xuất ra nội dung pre-rendered (ví dụ như “SSR” (Server-Side Rendering)).
- Tự động gửi form, test giao diện và nhập dữ liệu từ bàn phím,…
- Tạo môi trường testing tự động cập nhật. Chạy bản thử nghiệm trong Chorme với các tính năng mới nhất và phiên bản javascript mới nhất.
- Ghi lại timeline trace cho website của bạn giúp phát hiện sớm các vấn đề về hiệu năng.
- Test Chorme Extensions.
Trong bài viết này, mình sẽ cùng các bạn thử dùng puppeteer để chụp ảnh màn hình hoặc xuất file pdf nhé Các tính năng khác, mình hẹn nhau trong tương lai nhé
2. Một số hàm thông dụng
2.1 sentayho.com.vnch([options])
Hàm launch([options]) sẽ trả về một instance của brower với options là các cấu hình tùy chọn cho trình duyệt
Một số options:
Options Descrption Type Default product Tùy chọn browser, có thể là chorme hoặc firefox String ignoreHTTPSErrors Bỏ qua HTTPs errors trong quá trình điều hướng Boolean false headless Run browser ở chế độ headless Boolean true executablePath Text String Text slowMo Làm chậm các thực thi của puppeteer theo milliseconds Number defaultViewport Đặt chế độ xem trang gồm: width, height, deviceScaleFactor , isMobie, hasTouch, isLandscape Object args Đối số bổ sung để lựa chọn phiên bản trình duyệt Array<String> ignoreDefaultArgs Bỏ qua sentayho.com.vnultArgs(). Đây là một option khá nguy hiểm, cần cẩn thận khi sử dụng boolean|array<string> false handleSIGINT Đóng trình duyệt với Ctrl + C boolean true handleSIGTERM Close the browser process on SIGTERM boolean true handleSIGHUP Close the browser process on SIGHUP boolean true timoeout Thời gian milliseconds tối đa để start browser. Đặt 0 nếu không muốn xét timeout Number 30000 dumpio Whether to pipe the browser process stdout and stderr into sentayho.com.vn and sentayho.com.vn boolean false userDataDir Đường dẫn tới Thư mục của người dùng String env Thiết lập một số biến môi trường cho browser Object sentayho.com.vn devtools Tự động mở DevTools cho mỗi tab. Nếu options này là true thì headless phải là false Boolean pipe Kết nối với browser thông qua pipe thay vì WebSocket Boolean false extraPrefsFirefox Một số tùy chọn bổ sung khi dùng firefox Object
Trả về: <Promise<Browser>>
Chi tiết xem tại đây.
2.2 sentayho.com.vn(url[, options])
Hàm này sẽ điều hướng đến trang của browser đến website mà bạn muốn crawl dữ liệu hoặc chụp ảnh màn hình,…vv
Các tham số đầu vào:
- url: URL để điều hướng trang.
- options: Một số tùy chọn khi điều hướng
Options Description Type Default timeout Thời gian timeout tối đa, tính bằng miliseconds khi điều hướng String 30000 waitUntil Xem xét điều hướng thành công. Có 4 tùy chọn là load, domcontentloaded networkidle0 và networkidle2 stringArray<string> load referer Cung cấp referer header String
Trả về: <Promise<?Response>>
Lưu ý: Nếu có nhiều điều hướng, các xử lý sau sẽ được thực hiện ở điều hướng cuối cùng.
Chi tiết xem tại đây.
2.3 sentayho.com.vn([options])
Hàm sentayho.com.vn() sẽ thực hiện render file pdf từ trang html với các tùy chọn yêu cầu.
Một số options:
Options Descrption Type Default path Đường dẫn lưu file. Nếu không có path, file sẽ không được lưu. String scale Tỉ lệ của webpage. Nhận giá trị từ 0.1 đến 2 Number 1 displayHeaderFooter HIển thị header và footer Boolean false headerTemplate HTML template cho header. Bao gồm: date, title, url, pageNumber và totalPage Object footerTemplate HTML template cho footer. Options tương tự header. Text printBackground Tùy chọn in background Boolean false landscape Hướng giấy Boolean false pageRanges Phạm vi giấy để in, ví dụ: 1-5, 8, 11-13 Text format Định dạng, như Letter, A4, … String Letter width Chiều dài String Number height Chiều cao String Number margin Căn lề Object preferCSSPageSize Ưu tiên định dạng CSS so với các khai báo tùy chọn Boolean false
Trả về: <Promise<Buffer>>
Chi tiết xem tại đây.
3. Nghịch ngợm thôi nào
Đầu tiên, mình sẽ init một project Node trong folder test
mkdir test cd test npm init
Đừng quên cài puppeteer cho project nhé:
npm install pupperteer -save
Giờ thì mình sẽ viết file sentayho.com.vn để nghịch thử ahihi .
3.1 Chụp ảnh màn hình cái nhỉ
const puppeteer = require(‘puppeteer’); (async () => { const browser = await sentayho.com.vnch(); const page = await sentayho.com.vnage(); await sentayho.com.vn(‘https://viblo.asia’); await sentayho.com.vnenshot({path: ‘example.png’}); await sentayho.com.vne(); })();
Gõ lệnh run và chờ thành quả thôi nào:
node sentayho.com.vn
Kết quả:
3.2 Thử xuất một file pdf nha
const puppeteer = require(‘puppeteer’); (async () => { const browser = await sentayho.com.vnch(); const page = await sentayho.com.vnage(); await sentayho.com.vn(‘https://viblo.asia’, {waitUntil: ‘networkidle2’}); await sentayho.com.vn({ path: ‘viblo.pdf’, format: ‘A4’, printBackground: true, }); await sentayho.com.vne(); })();
Kết quả:
3.3 Chụp trang yêu cầu authenticate
Nếu bạn chụp một trang yêu cầu đăng nhập thì sẽ thế nào nhỉ.
Ví dụ: Ở dây, mình muốn chụp màn hình trang viết bài của trang Viblo.
const puppeteer = require(‘puppeteer’); (async () => { const browser = await sentayho.com.vnch(); const page = await sentayho.com.vnage(); await sentayho.com.vn(‘https://viblo.asia/publish/post’, {waitUntil: ‘networkidle2’}); await sentayho.com.vnenshot({ path: ‘viblo-authenticate.png’}) await sentayho.com.vne(); })();
Kết quả:
Như trong trường hợp này, chúng ta sẽ chụp được trang đăng nhập. Vì khi brower run và truy cập tới trang viết bài thì router được điều hướng sang trang đăng nhập vì trang mà chúng ta muốn truy cập yêu cầu authenticate.
Cách xử lý là chúng ta sẽ phải xét cookie trước khi truy cập trang web đó. Thử lại lần nữa nào:
const puppeteer = require(‘puppeteer’); (async () => { const cookie = { name: ‘viblo_auth’, value: ‘<your_cookie>’, // replace this! domain: ‘viblo.asia’, url: ‘https://viblo.asia’, path: ‘/’, httpOnly: true, secure: true, }; const browser = await sentayho.com.vnch(); const page = await sentayho.com.vnage(); await sentayho.com.vnookie(cookie); await sentayho.com.vn(‘https://viblo.asia/publish/post’, {waitUntil: ‘networkidle2’}); await sentayho.com.vnenshot({ path: ‘viblo-authenticate.png’}) await sentayho.com.vne(); })()
Kết quả bạn thu được sẽ như vầy nè
Chúc các bạn thành công và hẹn gặp lại các bạn ở các bài viết tiếp theo.
Tài liệu tham khảo: