難道爬蟲只能用
python
做? 不,我們上天的Node.js
也可以做!
- 需要準備的包
Node.js
的最新版本 下載地址 Node.js官網npm
包管理器下載 下載最新的官網版本Node.js
會自帶npm
npm
的第三方包puppeteer
在對應的js檔案內執行命令列工具npm i puppeteer -D
即可
爬蟲在獲取某些有保護機制的網頁時可能會失效
初入江湖 -自在地境篇
const puppeteer = require('puppeteer'); // 引入依賴
(async () => { //使用async函式完美非同步
const browser = await puppeteer.launch(); //開啟新的瀏覽器
const page = await browser.newPage(); // 開啟新的網頁
await page.goto('https://www.jd.com/'); //前往裡面 'url' 的網頁
const result = await page.evaluate(() => { //這個result陣列包含所有的圖片src地址
let arr = []; //這個箭頭函式內部寫處理的邏輯
const imgs = document.querySelectorAll('img');
imgs.forEach(function (item) {
arr.push(item.src)
})
return arr
});
await browser.close()
})()
複製過去 使用命令列命令 ` node 檔名 ` 就可以執行獲取爬蟲資料了
複製程式碼
這個
puppeteer
的包 ,其實是替我們開啟了另一個瀏覽器,重新去開啟網頁,獲取它們的資料。
瀟灑入世 -逍遙天境篇
-
上面只爬取了京東首頁的圖片內容,假設我的需求進一步擴大,需要爬取京東首頁 中的所有
<a> 標籤對應的跳轉網頁中的所有 title的文字內容,最後放到一個陣列中
。 -
我們的
async
函式上面一共分了五步, 只有puppeteer.launch()
,browser.newPage()
,browser.close()
是固定的寫法。 -
page.goto
指定我們去哪個網頁爬取資料,可以更換內部url地址,也可以多次 呼叫這個方法。 -
page.evaluate
這個函式,內部是處理我們進入想要爬取網頁的資料邏輯 -
page.goto
和page.evaluate
兩個方法,可以在async
內部呼叫多次, 那意味著我們可以先進入京東網頁,處理邏輯後,再次呼叫page.goto
這個函式,
注意,上面這一切邏輯,都是
puppeteer
這個包幫我們在看不見的地方開啟了另外一個 瀏覽器,然後處理邏輯,所以最終要呼叫browser.close()
方法關閉那個瀏覽器。
- 這時候我們對上一篇的程式碼進行優化,爬取對應的資源。
const puppeteer = require('puppeteer');
(async () => {
const browser = await puppeteer.launch();
const page = await browser.newPage();
await page.goto('https://www.jd.com/');
const hrefArr = await page.evaluate(() => {
let arr = [];
const aNodes = document.querySelectorAll('.cate_menu_lk');
aNodes.forEach(function (item) {
arr.push(item.href)
})
return arr
});
let arr = [];
for (let i = 0; i < hrefArr.length; i++) {
const url = hrefArr[i];
console.log(url) //這裡可以列印
await page.goto(url);
const result = await page.evaluate(() => { //這個方法內部console.log無效
return $('title').text(); //返回每個介面的title文字內容
});
arr.push(result) //每次迴圈給陣列中新增對應的值
}
console.log(arr) //得到對應的資料 可以通過Node.js的 fs 模組儲存到本地
await browser.close()
})()
複製程式碼
上面有天坑 page.evaluate函式內部的console.log不能列印,而且內部不能獲取外部的變數,只能return返回, 使用的選擇器必須先去對應介面的控制檯實驗過能不能選擇DOM再使用,比如京東無法使用querySelector。這裡由於 京東的分介面都使用了jQuery,所以我們可以用jQuery,總之他們開發能用的選擇器,我們都可以用,否則就不可以。
威震武林 -神遊玄境篇
資料在這個時代非常珍貴,上面兩個能獲取一些指定的特定資源,按照網頁的設計邏輯,選定特定的
href
的地址, 可以先直接獲取對應的資源,也可以通過再次使用page.goto
方法進入,再呼叫page.evaluate()
處理邏輯。 這裡就不做過多介紹了,畢竟Node.js
是可以上天的,或許未來它真的什麼都能做。這麼優質簡短的教程,請收藏 或者轉發給您的朋友,謝謝。