2.3.2.1. Cách làm truyền thống 2.3.2.1.1. Các bước thực hiện
Quá trình thu thập bài viết được chia thành các bước: Bước 1: Thu thập URL bài viết
Ở bước này chúng ta sẽ thu thập tất cả các đường dẫn URL ứng với các trang bài viết. Tất cả các trang báo điện tử hiện nay đều lưu trữ các bài viết theo các chuyên mục (category), việc làm này làm cho trang báo trực quan và thuận tiện cho người dùng khi muốn tìm kiếm thông tin. Với trang báo điện tử lớn như Dân trí thì ngoài các bài viết còn có rất nhiều các chuyên mục quảng cáo, các đường dẫn javascrips, các mục bài viết lồng nhau (ví dụ như phần tiêu điểm, tin nổi bật ...) chính vì thế vấn đề đặt ra trước hết là phải lọc được các URL bài viết theo các category, sau đó phải có một cơ
chếđể tránh lấy một URL nhiều lần.
Để lấy ra các đường dẫn URL ta có thể dùng hàm preg_math với $pattern là một biểu thức chính quy lấy ra các siêu liên kết. Kết quả thu được là một mảng với các phần tử
là các URL.
Sau đây là một ví dụ minh họa việc lấy ra các URL trong danh mục phapluat của trang Dân trí:
<?php
$crawler=file_get_contents('http://dantri.com.vn/c20s170/skphapluat/trang- 1.htm'); // duyệt nội dung của trang phapluat gán vào biến $crawler $pattern='/href="([^"]*)/is'; // biểu thức chính quy lấy ra các siêu liên kết preg_match_all($pattern ,$crawler,$matches);
print_r($matches[1]); ?>
43
Tiếp theo để lọc ra các URL bài viết trong danh mục pháp luật ta sẽ xử dụng các hàm tìm kiếm chuỗi trong PHP.
Ví dụ :
$result = array_unique($matches[1]); // đưa kết quả vào mảng unique foreach ($result as $url){ // duyệt từng phần tử
$find1= '.htm';
$find2= 's170'; // s170 là mã category
if ((strpos($link,$find1)==true) //lọc ra chuỗi có chứa chuỗi .htm &&(strpos($link,$find2)==true)) { //lọc ra chuỗi có chứa chuỗi s170 $content=file_get_contents('http://dantri.com.vn'.$url);
echo $content.'<hr>'; // in ra nội dung URL bài viết }
}
Bước 2: Bóc tách nội dung bài viết
Trước khi bóc tách thông tin ta sẽ sử dụng firebug – một add-ons của firefox, để xác
định các phần tử của trang web thông qua mô hình thẻ tag dạng cây.
Thông tin của một bài viết sẽđược bóc tách bằng cách sử dụng biểu thức chính quy và các hàm xử lý chuỗi trong PHP. Một bài viết sẽđược chia thành các trường thông tin
44
bao gồm : tiêu đề bài viết, giới thiệu bài viết, ảnh trong bài viết, nội dung bài viết, thời gian đăng bài viết và mã category tương ứng. Toàn bộ nội dung bài viết sau khi bóc tách xong sẽđược lưu vào cơ sở dữ liệu.
Sau đây là một ví dụ việc bóc tách nội dung một bài viết bất kỳ trên Dân trí lấy ra trường date time:
$link=”...” ; //$link là một URL bài viết bất kỳ
$crawler=file_get_contents("$link");
//duyệt nội dung của bài viết gán vào biến content $pattern = '/<div\sclass="neo-dtdate">(.*?)<\/div>/is';
// biểu thức chính quy lấy ra thời gian đăng bài viết preg_match_all($pattern ,$crawler,$matches);
foreach ($matches[1] as $date) {
echo "<b><h4>".$date."</h4></b>" ; // in ra kết quả
}
2.3.2.1.2. Nhận xét
Cách làm này có một số nhược điểm như sau: - Tốc độ thu thập chậm
Tốc độ thu thập chậm do phải duyệt nội dung hai lần. Lần đầu tiên là phải duyệt nội dung chuyên mục để lấy ra các URL bài viết, lần thứ hai là phải duyệt nội dung các bài viết để lấy ra các trường thông tin.
- Cơ sở dữ liệu quá lớn
Cơ sở dữ liệu lớn do phải lưu toàn bộ nội dung bài viết. Ta thử tưởng tượng chỉ với trang Dân trí đã có tới gần 400 nghìn bài viết, để lưu trữ cũng cần vài Gigabyte cơ sở
dữ liệu. Việc lưu trữ này sẽ vô cùng vất vả khi ta muốn tổng hợp thêm tin tức từ nhiều trang báo điện tử khác nhau. Vì là trang web tổng hợp thông tin nên nếu chỉ lấy nội dung từ một trang Dân trí thì không khả thi, trang web phải có khả năng tổng hợp thông tin từ nhiều nguồn thì mới có giá trị thương mại.
45
- Ngoài hai nhược điểm quan trọng kể trên thì còn một số nhược điểm khác trong quá trình hiển thị bài viết. Ví dụ như trong một bài viết có thể có nhiều ảnh đặc biệt là những bài phóng sự qua ảnh, khi đó cần cơ chế chung để chọn ra một ảnh đại diện để hiển thị ở phần mô tả bài viết. Mà các cơ chế này là khác nhau tùy vào từng trang báo. Do đó phần mô tả bài viết trong trang web tổng hợp thông tin sẽ không đảm bảo được tính toàn vẹn so với bài viết ở trang gốc.
Trong quá trình xây dựng trang web tôi đã nhận ra được các nhược điểm trong cách làm này, vì thế tôi đã tìm ra cách làm mới. Cách làm này có tốc độ thu thập nhanh hơn, cơ sở dữ liệu gọn nhẹ và đảm bảo được tính toàn vẹn của bài viết.
2.3.2.2. Cách làm mới
2.3.2.2.1. Các bước thực hiện
Quá trình thu thập bài viết được thực hiện qua các bước: Bước 1: Thu thập và bóc tách nội dung phần mô tả bài viết
Phần mô tả bài viết được minh họa ở hình 11. Trong phần này chúng ta sẽ thu thập các phần mô tả bài viết ứng với từng chuyên mục. Để làm được điều này ta cũng dùng hàm preg_math giống như cách làm truyền thống, trong đó $pattern là biểu thức chính quy để lấy ra phần mô tả. Sau đó ta sẽ thực hiện việc bóc tách nội dung phần mô tảđể
lấy ra các trường thông tin bao gồm : tiêu đề bài viết, giới thiệu bài viết, ảnh đại diện, URL bài viết. Trong URL bài viết ta lại lấy ra các trường: mã bài viết, mã chuyên mục, đường dẫn chuyên mục sau đó lưu tất cả vào cơ sở dữ liệu.
Sau đây là đoạn mã chương trình minh họa trình thu thập thực hiện việc thu thập phần mô tả bài viết:
function crawler($url){
$crawler = file_get_contents($url); // duyệt nội dung của trang ứng với url $pattern = '/<div\sclass=\"cat-headline\sclearfix\">(.*?)Xem\stiếp<\/a>/is';
//biểu thức chính quy lấy ra phần mô tả
preg_match_all($pattern ,$crawler,$matches); //kỹ thuật so trùng để lấy kết quả
46
$find1= '.htm'; // tìm kiếm chuỗi có đuôi htm if (strpos($link,$find1)==true) { add_into_db($link); // gọi hàm bóc tách nội dung } } }
Bước 2: Hiển thị nội dung bài viết
Sau khi đã lấy được nội dung các phần mô tả và lưu vào cơ sở dữ liệu, lúc này ta sẽ
thực hiện bước hiển thị nội dung ra trang web. Vì phần mô tả bài viết được lấy hoàn toàn từ trang gốc nên ta chỉ quan tâm đến việc hiển thị nội dung các bài viết. Do nội dung các bài viết không được lưu trong cơ sở dữ liệu nên khi ấn vào một đường dẫn bài viết thay vì lấy nội dung từ cơ sở dữ liệu ta sẽ gọi hàm bóc tách nội dung bài viết. Hàm bóc tách nội dung bài viết được xây dựng giống như trong cách làm truyền thống. Ý tưởng sáng tạo ở đây là: Trình thu thập lúc này không cần phải thu thập mà chỉ có nhiệm vụ bóc tách nội dung bài viết mà tốc độ bóc tách một bài viết của trình thu thập là rất nhanh nên ta không cần lưu vào cơ sở dữ liệu.
2.3.2.2.2. Nhận xét
Cách làm mới có một sốưu điểm sau: - Tốc độ thu thập nhanh hơn đáng kể
Tốc độ thu thập nhanh do hai lý do: thứ nhất là trình thu thập chỉ phải duyệt nội dung một lần (duyệt nội dung category) và thứ hai là lượng dữ liệu thu thập ít hơn nhiều. - Cơ sở dữ liệu gọn nhẹ
Cơ sở dữ liệu giảm khoảng hơn 10 lần do không phải lưu nội dung các bài viết, kiểm thử bằng cách thu thập 15000 bài viết, ở cách làm truyền thống cơ sở dữ liệu là hơn 100Mb trong khi cách làm này cơ sở dữ liệu chỉ có 9Mb.
- Đảm bảo tính toàn vẹn cho tài liệu gốc
Phần mô tả bài viết và phần nội dung bài viết mới là giống với bài viết gốc do đó đảm bảo được tính toàn vẹn của bài viết gốc.
47
2.4. THIẾT KẾ
Một sốđặc điểm của website:
- Website được viết bằng ngôn ngữ lập trình PHP tương tác với cơ sở dữ liệu MySQL.
- Website là một trang web tích cực.
- Website thực hiện việc thu thập bài viết từ trang báo điện tử lớn là Dân trí (http://dantri.com.vn). Tên các chuyên mục được lấy giống như trang Dân trí. Quá trình thu thập và bóc tách bài viết là tựđộng.
- Thuật toán sử dụng để thu thập dữ liệu là thuật toán tìm kiếm theo chiều rộng. - Phần chuyên mục (category) của website được viết bằng ajax nên có độ tùy biến cao.
2.4.1. Cấu trúc cơ sở dữ liệu 2.4.1.1. Danh sách các bảng
STT Tên Mô tả
1 category Bảng các category
2 news Bảng nội dung các bài viết được thu thập
2.4.1.2. Chi tiết các bảng
48
STT Thuộc tính Kiểu Miền giá trị Ghi chú
1 cate_id int 11 Khóa chính 2 cate_name varchar 30
3 cate_code varchar 11 Quan hệ với bảng news 4 cate_path varchar 30
5 cate_parent int 11
- Ý nghĩa của các thuộc tính:
+ cate_id: Số thự tự của category trong bảng category, tựđộng tăng dần + cate_name: Tên của category
+ cate_code: Mã của category
+ cate_path: Đường dẫn tương đối của category + cate_parent: Số category cha
- Bảng news trong cấu trúc cơ sở dữ liệu
STT Thuộc tính Kiểu Miền giá trị Ghi chú
1 news_id int 11 Khóa chính 2 news_title varchar 1000
3 news_img text 1000 4 news_link varchar 1000 5 news_intro text
6 news_num varchar double 7 cate_code varchar 11
49
- Ý nghĩa các thuộc tính:
+ news_id: Số thự tự của bài viết trong bảng news, tựđộng tăng dần + news_title: Tiêu đề của bài viết
+ news_img: Đường dẫn ảnh trong bài viết + news_link: Đường dẫn của bài viết + news_intro: Phần giới thiệu của bài viết + news_num: Mã bài viết
2.4.2. Phần quản trị cơ sở dữ liệu
Phần quản trị cơ sở dữ liệu được thiết kế trực quan, rất dễ sử dụng. Người dùng có thể lựa chọn thu thập bài viết từ một hoặc nhiều chủ đề, cũng có thể chọn chủ đề
mình thích hoặc lựa chọn thu thập tất cả các chủ đề. Đây là giao diện chính của phần quản trị:
50
2.4.3. Phần giao diện chính trang web
Giao diện chính được thiết kếđơn giản, đẹp mắt, dễ sử dụng. Cấu trúc trang web giống với cấu trúc của các trang báo điện tử lớn nên thuận tiện cho việc tra cứu, các chủđềđược sắp xếp một cách khoa học.
Hình dưới đây mô tả giao diện chính của trang web tổng hợp thông tin:
51
CHƯƠNG 3: KẾT LUẬN
Trong khoảng thời gian ba tháng từ khi nhận đề tài đến khi hoàn thành xong khóa luận, tôi đã có những cố gắng nhất định và đã đạt được một số kết quả bước đầu. Bằng sự nỗ lực của bản thân và sự giúp đỡ tận tình của thầy Hoàng Xuân Huấn tôi đã hoàn thành xong khóa luận tốt nghiệp với đề tài: “Tìm hiểu trình thu thập web và xây dựng trang web tổng hợp thông tin”.
3.1. CÁC KẾT QUẢ ĐÃ ĐẠT ĐƯỢC
- Tìm hiểu được kiến trúc của trình thu thập web, cơ chế hoạt động của một trình thu thập web cơ bản, các chiến lược thu thập dữ liệu, cơ chế đánh giá các trang web của các trình thu thập.
- Từ những kiến thức thu được trong quá trình tìm hiểu về trình thu thập web, tôi
đã hướng đến xây dựng một ứng dụng sử dụng trình thu thập web để thu thập bài viết tựđộng từ các trang báo điện tử lớn của Việt Nam. Ứng dụng bước đầu là thu thập các bài viết từ trang Dân trí đã hoạt động tốt, đảm bảo được các tiêu chí: tốc độ thu thập nhanh, cơ sở dữ liệu gọn nhẹ, đảm bảo tính toàn vẹn của các bài viết gốc.
- Giao diện phần quản trị được thiết kế trực quan, dễ sử dụng, thuận lợi cho người sử dụng, có độ tùy biến cao. Người dùng có thể lựa chọn thu thập bài viết từ
một hoặc nhiều chủđề, cũng có thể chọn chủđề mình thích hoặc lựa chọn thu thập tất cả các chủđề.
- Giao diện của trang web được thiết kế đơn giản, đẹp mắt, bố cục khoa học, thuận tiện cho việc tìm kiếm.
3.2. HƯỚNG PHÁT TRIỂN CỦA ĐỀ TÀI
Do thời gian thực hiện khóa luận có hạn nên tôi chưa thể thực hiện trọn vẹn ý tưởng tổng hợp các bài viết từ nhiều trang báo khác nhau. Nếu được phát triển thêm tôi sẽ nghiên cứu thêm cách tổng hợp các chuyên mục một cách tự động từ đó sẽ hoàn thành ý tưởng của mình một cách trọn vẹn. Về mặt lý thuyết tôi sẽ tìm hiểu kỹ hơn về
52
Hướng phát triển tiếp theo của đề tài là xây dựng một hệ thống máy tìm kiếm thông tin dựa trên cơ sở dữ liệu thu thập được.
53
TÀI LIỆU THAM KHẢO
[1] Gautam Pant, Padmini Srinivasan, Filippo Menczer. Crawling the Web. Web Dynamics 2004, pp 153-178
[2] Sriram Raghavan, Hector Garcia-Molina. Crawling the Hidden Web. Computer Science Department, Stanford University, USA 2001.
[3]Soumen Chakrabarti. Mining the Web: Discovering knowledge from hypertext
data. Elsevier Science, Morgan Kaufmann Publishers 2003.
[4] HồĐắc Phương. Mạng máy tính. NXB Đại học Quốc gia Hà Nội 2007. [5] Đinh mạnh Tường. Cấu trúc dữ liệu và thuật toán. Nhà xuất bản khoa học và kỹ thuật 2000.
[6] Wikipedia, http://en.wikipedia.org
[7] World Wide Web Consortium (W3C), http://www.w3.org [8] Bách khoa toàn thư tiếng Việt, http://vi.wikipedia.org
[9] Biểu thức chính quy, http://www.phpvn.org/index.php?topic=204.0 [10] Google, http://www.google.com.vn
[11] Hàm xử lý chuỗi, http://www.aweb.vn/xem-thiet-ke-web/61.Ham-tim-kiem- chuoi.html
[12] MySQL, http://phpcodevn.com
[13] Robot Exclusion Protocol, http://www.vietseo.net/indexability/googlebot- va-robotstxt/