一切都是為了偷懶!

身為一個替代役,除了每日基本的影印、蓋章、送公文之外,每個月我要整理一份將近 3,000 筆的停車資料,因為目前系統下載的報表中不包含車輛單位,所以必須手動一筆一筆到系統後台查詢,恰巧我當時看到一篇介紹 Node.js 爬蟲的文章 [Node.js] 用 request + cheerio 抓取即時天氣,馬上激起我決定用爬蟲來解決目前手動一筆一筆查詢的困擾!

一開始就遇到個大問題,怎麼模擬登入?!

雖然文章清楚解釋抓取資料的過程和方法,但我依樣畫葫蘆後卻只抓到了 “登入”、”忘記密碼” 等這些文字,原來我被擋在登入畫面啦!!!搜尋了很久,或許是沒有用到對的關鍵字搜尋,我一直找不到有相關模擬登入的案例分享QAQ卡了很久,於是我反過來開始思考,這學期我是怎麼設計登入流程?如果這個系統也是這樣設計,我是否可以拆解出登入的流程步驟,然後用機器模仿使用者行為進行登入,於是我寫下:

登入流程設計:

  1. 當訪客請求:新增一個 session,並把 session id 加進 cookie 回應給瀏覽器。
  2. 當訪客帶上 cookie 登入:進行帳密驗證,接著 Passport 的 serialize 會幫我把這個 user 存在伺服器端的 session 資料。
  3. 之後請求都帶有 cookie:確認 session 的合法性,Passport 的 deserialize 會透過 session 資料,取回剛剛登入的 user。

模擬登入步驟:

  1. 取得伺服器傳送過來的 cookie,裡面有 session id。
  2. 帶上帳號、密碼和剛剛取得的 cookie,然後用 Post 方法進行登入。
  3. 之後抓取頁面時都帶上 cookie。

有了明確的步驟後,我開始搜尋:如何取得 cookie?如何帶上帳號、密碼進行 Post 方法?馬上就找到了相應的解法,也成功模擬登入抓取到頁面上的資料!

欸!怎麼有亂碼…

成功抓取到頁面資料後,我開始設定每一筆資料要鎖定哪些頁面元素來抓取裡面的文字,其中,有一項資料要連到一個外部網站才能拿到資料,但取得到的內容怎麼都是亂碼啊?!搜尋了一下發現這是蠻常見當網站是使用 Big5 編碼的問題,也找到了相對應的套件分分鐘處理完畢,最後為了輸出成 .csv 檔又找了一個套件做處理,現在只要用這個爬蟲程式 30 秒就能完成過去每個月要花 6 小時才能整理完的資料,到目前為止算是成功達成目標!

就這樣寫出了 Callback Hell!

為了證明以上故事屬實,有程式有真相,這就是最後的程式碼,恩…完全實現了課程中提到的 Callback Hell,超極難看懂的啦!我開始用最近學到的 async/await 重構,這是重構後的程式碼,雖然還是寫得很爛,但修改後從 19-29 行能大致了解整個程式碼做了什麼事情,之後要修改也會更容易。

下一個,爬什麼?!

回顧整個過程,除了學到不少新工具和套件,應用到 AC 扎實課程的內容,更寶貴的是自行解決問題的經驗,有了這次爬蟲的經驗我也開始了另一個新的計畫,結合過去行銷工作的經驗,打算做一個台灣最大群眾募資平台嘖嘖的分析工具,學期四再和大家分享到底有沒有成功呢!