任務:把上週爬取每週文章的標題和發佈日期存到SQLite資料庫
前言
用Python網頁爬蟲取得資料後,最後一個步驟,會想把資料存到資料庫裡,今天以SQLite為例分享實作部分。
為什麼我要用SQLite?
SQLite是非常輕量型的關聯式資料庫,所以比較適用於小型應用程式,比如APP,存放資料量沒那麼大的應用程式,也是跨平台資料庫,它和一般企業級資料庫(Mysql……),最不一樣的地方是企業級資料庫都會有server,server也就是資料庫,用戶端這邊通常就要安裝,這個資料庫的客戶端,有點像是小的驅動程式,那我們要存取資料庫的時候,就是要用客戶端去跟資料庫的server進行存取還有資料的操作。那SQLite資料庫非常簡單,就是安裝後,用戶端就可以直接執行,可以直接存取資料庫裡面的資料,簡單來講,一個資料庫就是一個檔案,雖然輕量型,但大部分.sql的語法都有支援,而且也是一個免費的資料庫。
第一步驟:安裝DB Browser for SQLite,用這個工具去建立資料庫
- 建立一個資料庫,然後在資料庫裡建立一個資料表,命名為post。在資料表裡定義儲存的欄位。先建立一個title的欄位,它的類型是text(字串),再建立一個來存發布日期的欄位publish,一樣定義類型是text(字串)
- 在爬蟲專案資料夾底下新建資料庫,存檔
第二步驟:使用python串列的資料結構來進行儲存,把資料打包成包裹
定義result串列,每次爬到標題和發佈日期後,就要把它存起來,存到串列裡。👩🏻💻results.append((title.getText().strip(),) + (published.getText().strip(),))
- 把每一篇文章的標題和發佈日期打包成元組(tuple),如果只有一個值最後要加逗點,這樣python才知道這是一個元組(tuple)
- 把標題和發佈日期加入串列裡面(results.append),append是加入的意思(有for就會把每次標題和發佈日期全部都加入串列裡)
🔍元組的賦值:a,b = 1, 2
第三步驟:寫入sq資料庫
- sq資料庫內建在python裡面,直接👩🏻💻import sqlite3這個模組,接下來把網頁爬蟲專案連結到資料庫,用👩🏻💻conn = sqlite3.connect(“inside.db”)
- inside.db是路徑
- 操作資料庫的動作👩🏻💻cursor = conn.cursor(),用連線物件去建立cursor物件
- 接下來定義要進行寫入資料的指令👩🏻💻sql = “INSERT INTO post(title, published)VALUES(?, ?)”
- 寫入兩個欄位(title, published)
- 接下來要指定值VALUES(?, ?),有兩個值所以就是兩個問號,這樣python才知道要塞幾個值給這個指令
- 跑for 迴圈👩🏻💻for result in results: cursor.execute(sql, result)
- 用cursor去執行寫入資料的指令,指令裡面要給它值就是result(網頁爬蟲所取到的資料)
- 全部都寫入後在最外層要給確定,讓這些資料都確認完成👩🏻💻conn.commit()
第四步驟:執行code
在資料庫的資料表可以用右鍵>browse table,看這個table的資料內容,把網頁爬蟲所取得到的每一筆對應的文章標題和日期都寫進來
Mike提供的完整程式碼:
from bs4 import BeautifulSoup import requests import sqlite3 response = requests.get("https://www.inside.com.tw/tag/AI") soup = BeautifulSoup(response.content, "lxml") cards = soup.find_all("div", {"class": "post_list_item"}) results = [] for card in cards: title = card.find("h3", {"class": "post_title"}) published = card.find("li", {"class": "post_date"}) print(f"標題:{title.getText().strip()}") print(f"日期:{published.getText().strip()}") results.append((title.getText().strip(),) + (published.getText().strip(),)) # print(f"標題:{title.getText().strip()}") # print(f"日期:{published.getText().strip()}") conn = sqlite3.connect("inside.db") # 連接資料庫 cursor = conn.cursor() sql = "INSERT INTO post(title, published)VALUES(?, ?)" # 寫入資料的SQL指令 for result in results: cursor.execute(sql, result) # 執行寫入資料的SQL指令 conn.commit() # 儲存