Cách crawl dữ liệu web bằng Python

Cách crawl dữ liệu web hay cách thu thập dữ liệu web là một thắc mắc của khá nhiều bạn. Lý do bởi hiện nay, có vô vàn các website ở đủ mọi lĩnh vực cung cấp cho chúng ta rất nhiều thông tin hữu ích. Đôi khi, chúng ta sẽ muốn tổng hợp lại các thông tin này lại một chỗ để có thể dễ dàng sử dụng, phân tích,… Do vậy, bài viết này Lập Trình Không Khó sẽ hướng dẫn bạn các kiến thức cơ bản nhất về cách crawl (thu thập) dữ liệu web và có một vài demo bằng ngôn ngữ Python.

Để có thể nắm được tốt nhất nội dung của bài viết này, người đọc nên có sẵn 1 số kiến thức/kinh nghiệm sau:

  • Nắm được cấu trúc của 1 website.
  • Có kiến thức về HTML, CSS selector, XPath
  • Có kiến thức căn bản về ngôn ngữ lập trình Python
  • Có am hiểu nhất định về Dev Tools của trình duyệt

Nếu bạn không có sẵn các chuyên môn yêu cầu phía trên thì cũng không cần quá lo lắng. Bạn vẫn có thể nắm được cơ chế hoạt động, các kiến thức cơ bản và thực hành cùng tụi mình.

Lưu ý 1: Các kiến thức trong bài này áp dụng cho các website không áp dụng cơ chế lazy load. Thường sẽ là các website tin tức hay các website nhỏ. Trong khi đó khá nhiều website có cơ chế lazy load thì ngoài các kiến thức cơ bản trong bài viết này, ta sẽ cần các kỹ thuật nâng cao hơn.

Lưu ý 2: Trong quá trình thực hành, bạn chú ý tránh spam làm ảnh hưởng tới hoạt động bình thường của các website. Nếu cần, nên chạy vào ban đêm và để tốc độ vừa phải.

Chúng ta cùng bắt đầu nhé!

Kiến thức crawl dữ liệu web

Mã nguồn của trang (Page source)

Mọi web page của một trang web bất kỳ mà bạn nhìn thấy đều được trình duyệt vẽ lên từ 1 source code (bao gồm: html, css, js, json,…) mà máy chủ của website đó trả về cho trình duyệt.

Mỗi khi bạn yêu cầu xem 1 trang nào đó (ví dụ: truy cập url facebook.com), thì trình duyệt sẽ gửi yêu cầu đó về máy chủ. Máy chủ xử lý yêu cầu và gửi phản hồi lại là 1 source code (page source, do webserver sinh ra). Trình duyệt tiếp nhận page source này và hiển thị nội dung đẹp đẽ cho chúng ta coi.

Tất cả những gì trình duyệt hiện lên (cái chúng ta thấy) đều được lấy từ page source đó. Do vậy, về nguyên lý thì tất cả những gì bạn thấy trên trang web đều có thể thu thập được bằng ngôn ngữ lập trình.

Vậy, nếu chúng ta dùng ngôn ngữ lập trình để gửi yêu cầu tới một url nào đó, thì cái chúng ta nhận được cũng sẽ là page source. Và việc cần làm của chúng ta là tìm nội dung mình cần trong cái page source đó.

Lưu ý:

  1. Bạn có thể xem page source của 1 trang web bất kỳ bằng tổ hợp phím Ctrl + U hoặc kiểm tra phần tử bằng tổ hợp Ctrl + Shift + I. Với MacOS thì thay Ctrl bằng Cmd, bạn cũng có thể thấy chúng khi click chuột phải trên trang.
  2. Một số website sẽ chặn cách phía trên, ta vẫn có thể xem mã nguồn trên trình duyệt bằng cách truy cập địa chỉ: view-source:<url_cần_xem> như cách ta truy cập 1 trang web.
  3. Bạn cần có kiến thức cơ bản về HTML, CSS, JS để có thể hiểu mã nguồn này. Nếu không, bạn có thể thử tìm kiếm (Ctrl + F) từ khóa mình cần thử xem có không.

Mã nguồn của trang (page source) là dữ liệu có cấu trúc. Chúng ta hoàn toàn có thể biểu diễn nó dưới dạng cấu trúc dữ liệu Tree (cây). Qua đó, bạn có thể duyệt qua từng node trên cây, tìm kiếm và lấy giá trị của node bất kỳ trên cây đó.

Tìm kiếm phần tử

Khi có được mã nguồn của trang, chúng ta sẽ tìm kiếm đến những vị trí mà ta cần để lấy dữ liệu cần thiết. Quá trình đó có thể thực hiện bằng một số cách dưới đây:

Tìm kiếm theo CSS Selector

Nếu bạn đã từng dùng JS hoặc JQuery thì chắc không còn lạ với CSS Selector. Từ mã nguồn sau khi được “làm đẹp”, chúng ta có thể dùng css selector để đi tới phần tử chúng ta cần.

Lấy ví dụ một đoạn mã nguồn sau:

  • Giá trị của các thuộc tính id (ex: top-site) thường sẽ là duy nhất trên mỗi webpage. Trong selecter thì class đại diện bởi dấu thăng (#) trước nó.
  • Giá trị của các thuộc tính class (ex: container, item, col-xs-6) có thể lặp lại nhiều lần trên mỗi webpage. Trong selecter thì class đại diện bởi dấu chấm (.) trước nó.
  • Các thẻ (ex: div, h3, p,…) là các tagname.

Ví dụ dùng css selector để tìm tới thẻ h3 có chứa giá trị Danh sách website:

  • div.container > h3#top-site
  • div > h3#top-site
  • #top-site

Tìm kiếm theo XPath

Nếu coi page source là một file xml thì ta có cách tìm kiếm theo XPath. Ví dụ dùng css selector để tìm tới thẻ h3 (trong ví dụ trên) có chứa giá trị Danh sách website:

  • /html/body/div/h3
  • //*[@id=”top-site”]

Về cách này, mình không quá rành nên xin phép không bàn thêm.

Cách lấy CSS Selector/XPath của phần tử

Trên trình duyệt, bạn cũng có thể dễ dàng copy selector hoặc xpath bằng cách chuột phải vào phần tử tại Dev Tools (Ctrl + Shift + I) như hình dưới đây:

Cách copy CSS Selector hoặc XPath trên Dev Tools của trình duyệt
Cách copy CSS Selector hoặc XPath trên Dev Tools của trình duyệt

Xem gif để dễ hình dung hơn cách lấy xpath/css selector của một phần tử bất kỳ:

Cách lấy xpath, selector của một element trên webpage
Cách lấy xpath, selector của một element trên webpage

Quy trình: Đặt chuột vào phần tử cần lấy -> Click chuột phải -> Inspect -> Chuột phải vào source của nó -> Copy -> Copy Selector/Xpath.

Các thư viện crawl dữ liệu trong Python

Có thể nói, Python là ngôn ngữ đơn giản nhất giúp bạn có thể viết script crawl dữ liệu website nhanh chóng. Lý do bởi bản thân ngôn ngữ nó hỗ trợ rất tốt, lại còn kho tàng thư viện có sẵn hỗ trợ tận răng. Đó cũng là lý do mình chọn ngôn ngữ này để demo trong bài viết này.

# Thư viện requests

Với thư viện này, bạn có thể dễ dàng thực hiện gửi các yêu cầu (request) tới địa chỉ bất kỳ. Sau đó bạn sẽ nhận được phản hồi dưới dạng page source. Các chức năng cơ bản của thư viện này:

  • Tạo request, có thể có tham số (url params, body params, …) theo method bất kỳ (GET, POST, …)
  • Đọc phản hồi của máy chủ ở các format khác nhau (raw, json, media, …)
  • Gửi kèm Cookies, Auth, …

Thông tin thêm:

  • Cài đặt: pip install requests
  • Source: https://docs.python-requests.org/en/latest/

# Thư viện beautifulsoup4

Thư viện này sẽ hỗ trợ bạn “làm đẹp” cái source mà bạn nhận được mỗi khi gửi request. Sau khi làm đẹp, bạn có thể thực hiện mọi thao tác tìm kiếm, trích xuất giá trị mà mình cần tìm từ source.

Thông tin thêm:

  • Cài đặt: pip install beautifulsoup4
  • Source: https://www.crummy.com/software/BeautifulSoup/

# Dành cho website phức tạp

Với các website sử dụng cơ chế lazy load phức tạp. Các thành phần trên web chỉ yêu cầu tới máy chủ khi người dùng đang xem nó. Khi đó, một webpage mà bạn thấy được tạo ra bởi nhiều hơn 1 request (vd: Facebook, Instagram, …) đều có cơ chế này.

Ưu điểm của các thư viện này là chúng giả lập trình duyệt luôn, nên không bỏ sót bất kỳ request nào. Nhưng như vậy ta phải tải tất cả nội dung mà có thể chẳng cần đến, dẫn đến quá trình thu thập sẽ chậm hơn nhiều.

Do đây là bài hướng dẫn cơ bản, mình sẽ không đi sâu vào dạng phức tạp này.

Thực hành thu thập dữ liệu web

Trong mục này, chúng ta sẽ cùng thực hành một vài ví dụ thực tế cách crawl dữ liệu web với ngôn ngữ Python.

# Vd1. Thu thập thông tin bài báo CNN

Trong ví dụ này, mình sẽ sử dụng ngôn ngữ Python và các thư viện requests, beautifulsoup để lấy các thông tin cần thiết từ 1 bài báo trên CNN.

  • Cài các thư viện cần dùng: pip install requests beautifulsoup4 lxml
  • Xem trước URL: https://edition.cnn.com/2021/10/03/uk/everard-uk-police-gbr-cmd-intl/index.html

Kết quả thực thi:

# Vd2. Thu thập tag phổ biến trên StackOverflow

  • Cài các thư viện cần dùng: pip install requests beautifulsoup4 lxml
  • Xem trước: https://stackoverflow.com/tags
  • Với mỗi tag, mình sẽ lấy: tên tag, mô tả ngắn, số câu hỏi theo ngày, tuần và tổng số, số người theo dõi tag đó.
Cấu trúc của phần thẻ tags trên wesbite
Cấu trúc của phần thẻ tags trên wesbite

Source code kèm giải thích:

Kết quả chạy:

# Vd3. Sử dụng Github API yêu cầu đăng nhập

  • Cài đặt thư viện cần thiết: pip install requests
  • Github API docs: https://docs.github.com/en/rest
  • Để dùng Github API, ta cần phải đăng nhập để sử dụng. Do đó, ví dụ này mình sẽ demo cách dùng thư viện trong Python để đăng nhập (auth) của Github và lấy một số thông tin cá nhân trên Gihub của mình.

Kết quả chạy:

# Ví dụ sử dụng Selenium

Với Selenium, nếu bạn đọc quan tâm có thể theo dõi các bài viết trong series Selenium không khó, series này bao gồm:

  • Hướng dẫn cơ bản & cài đặt môi trường Selenium
  • Ví dụ đăng nhập Facebook với Selenium
  • Ví dụ lấy danh sách video của playlist bất kỳ

Lập Trình Không Khó có cung cấp dịch vụ thu thập & phân tích dữ liệu web, bạn đọc quan tâm có thể tham khảo chi tiết & liên hệ sử dụng dịch vụ TẠI ĐÂY 

Bài viết liên quan

Cảm ơn các bạn đã theo dõi bài viết hướng dẫn crawl dữ liệu website với Python. Trong quá trình tìm hiểu, thực hành. Nếu bạn đọc có thắc mắc thì có thể đặt câu hỏi tại:

Sáng lập cộng đồng Lập Trình Không Khó với mong muốn giúp đỡ các bạn trẻ trên con đường trở thành những lập trình viên tương lai. Tất cả những gì tôi viết ra đây chỉ đơn giản là sở thích ghi lại các kiến thức mà tôi tích lũy được.
Subscribe
Notify of
guest
0 Bình luận
Inline Feedbacks
View all comments