iT邦幫忙

第 11 屆 iThome 鐵人賽

DAY 9
2
AI & Data

爬蟲在手、資料我有 - 30 天 Scrapy 爬蟲實戰系列 第 9

【Day 8】蒐集 iT 邦幫忙的技術文章 (1/6) - 列表頁

終於進入最令人期待的環節了!(有人期待嗎QQ)接著四天會試著蒐集 iT 邦幫忙的技術文章,從列表頁開始,把每篇文章的標題、內文、回應和留言都蒐集起來。

接下來的實作都建議大家使用虛擬環境了喔!記得先執行 pipenv shell

載入網頁原始碼

Day 7 中,我們有學到怎麼拿到網頁原始碼,這邊用簡單的 GET 請求即可,同時利用 Day 5 學到的 BeautifulSoup 來載入網頁原始碼。

import requests
from bs4 import BeautifulSoup

html_doc = requests.get('https://ithelp.ithome.com.tw/articles?tab=tech').text
soup = BeautifulSoup(html_doc, 'lxml')

print(soup.prettify())

https://ithelp.ithome.com.tw/upload/images/20190923/20107875xyJn04oTBi.png

定位資料

先在畫面上確認我們要蒐集的資料範圍。例如我們要抓到畫面上第一篇文章「js型態轉換與查詢js型態」:(後面截圖或執行的時候第一篇文章會一直變.....畢竟鐵人賽期間更新很快)

https://ithelp.ithome.com.tw/upload/images/20190923/20107875bWwefpw87h.png

這時候可以用 Chrome 的開發人員工具來定位資料在原始碼中的位置,開啟開發人員工具的方式有幾種:

  1. F12
  2. Ctrl + Shift + I
  3. 管理 > 更多工具 > 開發人員工具

https://ithelp.ithome.com.tw/upload/images/20190923/20107875CeIgS7910w.png

  1. 右鍵 > 檢查

https://ithelp.ithome.com.tw/upload/images/20190923/20107875Wizh1cj0ka.png

打開後就可以看到下方多出一個區塊,紅框內是目前畫面上的 HTML 原始碼,這就是爬蟲很重要的工具之一啦!

https://ithelp.ithome.com.tw/upload/images/20190923/20107875d8Ii0z9stp.png

如果開發人員工具不在下方,或者想要顯示在其他位置的話,可以點選右上方三個點的圖標,在「Dock side」中選擇要顯示的位置,左到右分別為:另開視窗、靠左,置底,靠右。

https://ithelp.ithome.com.tw/upload/images/20190923/20107875RpK4OTeRIA.png

這時候有兩種方式可以快速定位我們想要的資料:

  1. 在文章標題上「右鍵 > 檢查」

https://ithelp.ithome.com.tw/upload/images/20190923/20107875xgS20BE98u.png

  1. 點選開發人員工具左上角的「選取工具」,再點選文章標題

https://ithelp.ithome.com.tw/upload/images/20190923/20107875UcPmzl4GcN.png

這時候就可以看到下方的原始碼中,反白灰色區塊會跳到我們定位的文章標題了。

https://ithelp.ithome.com.tw/upload/images/20190923/20107875Tg2E72OJEw.png

使用選擇器

Day 6 我們有學到怎麼在程式中找到目標資料,但是...現實中的 HTML 結構這麼複雜,要怎麼快速在 HTML 結構中找出文章標題呢?這時候有個偷懶的方式,就是在原始碼中文章標題的標籤上按「右鍵 > Copy > Copy selector」。

https://ithelp.ithome.com.tw/upload/images/20190923/20107875qLO7SYNcU5.png

找個地方貼上,就會得到一串密密麻麻的東西:body > div.container.index-top > div > div > div.leftside > div.board.tabs-content > div:nth-child(1) > div.qa-list__content > h3 > a,這串就是第一篇文章標題的 CSS 選擇器,我們就可以拿來在程式中找到文章標題了。

title = soup.select_one('body > div.container.index-top > div > div > div.leftside > div.board.tabs-content > div:nth-child(1) > div.qa-list__content > h3 > a')
print(title.text)

https://ithelp.ithome.com.tw/upload/images/20190923/20107875slgAPbQ1WG.png

再次說明,這段時間一直有新文章出來,所以每個截圖、每次執行程式的結果都不一樣是很正常的

取得列表資料

今天的任務是要找出列表頁中所有文章標題,我們可以用剛剛的方式來取得每篇文章標題的 CSS 選擇器。

title1 = soup.select_one('body > div.container.index-top > div > div > div.leftside > div.board.tabs-content > div:nth-child(1) > div.qa-list__content > h3 > a')
title2 = soup.select_one('body > div.container.index-top > div > div > div.leftside > div.board.tabs-content > div:nth-child(2) > div.qa-list__content > h3 > a')
title3 = soup.select_one('body > div.container.index-top > div > div > div.leftside > div.board.tabs-content > div:nth-child(3) > div.qa-list__content > h3 > a')
# ...依此類推

別鬧啦!!!!!

除非是用程式行數算薪水再這樣幹

萬一網站改版了(真的常常發生!),會需要修改一大堆地方,非常不方便而且很容易漏改。人生苦短,我們可以用更有效率的方式來寫程式,把多出來的時間拿去看其他鐵人大大的文章。

要怎麼找到適用於所有文章標題的選擇器呢?可以先參考開發人員工具下方這排,雖然很冗長但很有參考價值,就先拿來試試看吧。

https://ithelp.ithome.com.tw/upload/images/20190923/20107875n5iS6ZLpff.png

title_tags = soup.select('html > body > div > div.row > div.col-md-12.clearfix > div.leftside > div.board.tabs-content > div.qa-list > div.qa-list__content > h3.qa-list__title > a.qa-list__title-link')

for title_tag in title_tags:
	print(title_tag.text)

https://ithelp.ithome.com.tw/upload/images/20190923/20107875FhmrVzgWDW.png

看來有成功抓到網頁上所有文章標題了,但有覺得這一長串選擇器看起來很難過嗎?其實要定位文章標題不需要這麼複雜的選擇器,詳情請待下回分解~


上一篇
【Day 7】請求和回應
下一篇
【Day 9】蒐集 iT 邦幫忙的技術文章 (2/6) - 使用好維護的選擇器
系列文
爬蟲在手、資料我有 - 30 天 Scrapy 爬蟲實戰33
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言