• Bỏ qua primary navigation
  • Skip to main content
  • Bỏ qua primary sidebar

Thủ thuật thiết kế website

Chia sẻ kinh nghiệm thiết kế website

  • Trang chủ
  • Joomla
    • Thủ thuật Joomla
    • Joomla Extensions
    • Joomla Themes
  • WordPress
    • Thủ thuật WordPress
    • WordPress Plugins
    • WordPress Themes
  • PHP Framework
    • Codeigniter
    • Laravel
    • Laminas
  • App Developer
    • React Native
    • Flutter
  • SEO
  • Chia sẻ
  • Phần mềm
Bạn đang ở:Trang chủ / PHP Framework / Laravel / Laravel Crawler Data cực kì đơn giản với Goutte

Laravel Crawler Data cực kì đơn giản với Goutte

14/09/2023 - Administrator Để lại bình luận

Data là một trong những yếu tô quan trọng trong bất kì ứng dụng hay trang web nào. Đặc biệt trong các dự án mới luôn cần có dữ liệu để vận hành các chức năng. Nhưng vấn đề ở đây, dự án mới thì lấy đâu ra data?, mà việc nhập tay sẽ mất rất nhiều thời gian, dữ liệu lại không sát với thức tế. Vậy làm sao có thể có data? Crawler Data chính là câu trả lời cho bạn.

Crawler Data là tự động hóa việc trích xuất thông tin từ một nguồn nào đó, cụ thể ở bài viết này là chúng ta sẽ lấy thông tin các bài tin tức trên một website

1. Chuẩn bị

Chuẩn bị cho project laravel (Php, Composer, Mysql) và config kết nối đến database.

Chúng ta sẽ cài đặt package Laravel-goutte nên các bạn hãy đọc trước.

Địa chỉ website mẫu.

Laravel Crawler Data cực kì đơn giản với Goutte
Ảnh để crawler data

2. Cài đặt package

Đầu tiên cài đặt package bằng composer

$ composer require weidner/goutte

Sau đó kiểm tra trong composer.json

"require": {
        "php": "^7.3|^8.0",
        "laravel/framework": "^8.54",
        "weidner/goutte": "^2.1"
    },

Sau khi cài đặt thành công thì các bạn khai báo trong config/app.php

return [
	'providers' => [

        // ...

        /*
         * Package Service Providers...
         */
        Weidner\Goutte\GoutteServiceProvider::class, // [1] This will register the Package in the laravel echo system

        // ...

    ],

    // ...

    'aliases' => [

        'App' => Illuminate\Support\Facades\App::class,
        'Artisan' => Illuminate\Support\Facades\Artisan::class,

        // ...

        'Goutte' => Weidner\Goutte\GoutteFacade::class,

        // ...
    ],

];

3. Migrations và Models

Để không làm project trở nên quá phức tạp, với mỗi bài viết, ta chỉ cần lấy thông tin là: title, content, description. Database tương ứng chỉ có một bảng duy nhất. Chạy lệnh sau để tạo 2 file model và migrations cho bảng posts.

$ php artisan make:model Post

Hàm up() trong file migration sẽ có nội dung như sau:

public function up()
{
    Schema::create('posts', function (Blueprint $table) {
        $table->id();
        $table->longText('title');
        $table->longText('content');
        $table->longText('description');
        $table->timestamps();
    });
}

Sau đó để tạo bảng trong CSDL thì chúng ta sẽ dùng câu lênh:

$ php artisan migrate

4. Crawler Data

4.1 Bắt đầu

Trước tiên, ta tạo 1 command line, các bạn cũng có thể sử dụng route, controller để thực hiện. Ta sẽ xử lý logic luôn trong command line

Tạo command line:

$ php artisan make:command ScrapePost

Vào file \app\Console\Commands\ScrapePost.php và chúng ta sẽ thực hiện logic trong đó.

4.2 Tìm hiểu cấu trúc HTML

Để crawl dữ liệu từ một website, trước tiên ta phải hiểu cấu trúc HTML của website đó được tổ chức thế nào. Điều này cũng đồng nghĩa, nếu có bất kì cập nhật nào của chủ website, làm thay đổi cấu trúc HTML thì scraper của ta có khả năng ở nên vô dụng.

Truy cập vào link, kiểm tra các phần tử của website:

Laravel Crawler Data cực kì đơn giản với Goutte
Phẩn tích ảnh muốn crawler

Một bài viết sẽ được chia làm 3 phần là title, description, content. Tất cả các bài ở cột bên trái mà chúng ta muốn cào sẽ có cấu trúc này. Trước tiên ta sẽ test cào phần title

Bạn F12 để inspect phần html của phần title. Phần title là thẻ h1 và có class là dt-news__title.

Laravel Crawler Data cực kì đơn giản với Goutte
thuộc tính của title

Tượng tự, bạn truy cập vào link để kiểm tra các phần description, content của website:

  • Tất cả description đều được đặt giữa thẻ h2
Laravel Crawler Data cực kì đơn giản với Goutte
thuộc tính của description
  • Content được năm trọn trong thẻ div có class “dt-news__content“
Laravel Crawler Data cực kì đơn giản với Goutte
thuộc tính của content

Lưu ý rằng cấu trúc HTML trên có thể đã thay đổi so với thời điểm bài viết được tạo ra, vì vậy, bạn nên tự mình vào link và tìm tòi. Đây có lẽ là công đoạn thú vị nhất trong toàn bộ quá trình.

4.3 Crawler Data thôi

Trước tiên, phần cào data này mình sẽ thực hiện login trên command line, các bạn có thể sử dụng route, controller để thực hiện.

Tạo command line

$ php artisan make:command ScrapePost

Truy cập vào thư mục /app/Console/Commands/ScrapePost.php để thực hiện logic trong đó.

Logic sẽ được xử lý trong handle(), link trong phần request GET là bài viết Người bán nhà phố để đi tìm “vùng xanh hạnh phúc”

Để test mình sẽ thực hiện lấy title của bài viết trước

// ScrapePost.php

/**
* The name and signature of the console command.
*
* @var string
*/
protected $signature = 'scrape:post';

/**
* The console command description.
*
* @var string
*/
protected $description = 'Command description';

/**
* Create a new command instance.
*
* @return void
*/
public function __construct()
{
parent::__construct();
}

/**
* Execute the console command.
*
* @return int
*/
public function handle()
{
    $crawler = GoutteFacade::request('GET', 'https://dantri.com.vn/lao-dong-viec-lam/can-tho-f0-f1-bot-lo-lang-vi-khong-phai-tra-vien-phi-20210829181940605.htm');
    $title = $crawler->filter('h1.dt-news__title')->each(function ($node) {
    	return $node->text();
    })[0];
    print($title);
}

Phần protected $signature = ‘command:name’; các bạn đổi tên thành ‘scrape:post’ nhé

Rồi bạn chạy command bằng terminal:

Laravel Crawler Data cực kì đơn giản với Goutte

Vậy là đã mình đã thành công lấy được title bài viết, giờ mình sẽ lấy các phần còn lại nhé.

//handle

$title = $crawler->filter('h1.dt-news__title')->each(function ($node) {
	return $node->text();
})[0];

$description = $crawler->filter('div.dt-news__sapo h2')->each(function ($node) {
	return $node->text();
})[0];
$description = str_replace('Dân trí', '', $description);

$content = $crawler->filter('div.dt-news__content')->each(function ($node) {
	return $node->text();
})[0];

Kết quả:
Laravel Crawler Data cực kì đơn giản với Goutte

Ta đã lấy thành công thông tin bài viết. Vậy để lấy thêm được nhiều bài viết khác nữa thì sao? Ở phần chuẩn bị, các bạn thấy các bài viết đều có cấu trúc html như bài mình cào, vậy chỉ cần lấy link của các bài viết thì mình cũng sẽ lấy được nội dụng bài viết đó.

Phần href mà mình cần lấy nằm trong thẻ h3 có class là news-item__title, mình sẽ chọc vào thẻ h3 lấy thẻ a và attr là href.

public function handle()
{
    $crawler = GoutteFacade::request('GET', 'https://dantri.com.vn/lao-dong-viec-lam.htm');
    $linkPost = $crawler->filter('h3.news-item__title a')->each(function ($node) {
    	return $node->attr("href");
    });

    foreach ($linkPost as $link) {
    	print($link . "\n");
    }
}
Laravel Crawler Data cực kì đơn giản với Goutte

Mình đã lấy ra mảng linkPost chứa link những bài viết, vậy mình chỉ cần dùng vòng lặp chọc vào từng link một và xử lý bằng logic lúc ban đầu để lấy title, description, content là mình có thể lấy được được hết nội dung của đống bài viết này rồi.

public function handle()
    {
        $crawler = GoutteFacade::request('GET', 'https://dantri.com.vn/bat-dong-san.htm');
        $linkPost = $crawler->filter('h3.news-item__title a')->each(function ($node) {
            return $node->attr("href");
        });

        foreach ($linkPost as $link) {
            $this->scrapeData($link);
        }
    }
    
public function scrapeData($url)
    {
        $crawler = GoutteFacade::request('GET', $url);

        $title = $this->crawlData('h1.dt-news__title', $crawler);

        $description = $this->crawlData('div.dt-news__sapo h2', $crawler);

        $description = str_replace('Dân trí', '', $description);

        $content = $this->crawlData('div.dt-news__content', $crawler);

        $dataPost = [
            'title' => $title,
            'content' => $content,
            'description' => $description
        ];

        Post::create($dataPost);
    }

protected function crawlData(string $type, $crawler)
    {
        $result = $crawler->filter($type)->each(function ($node) {
            return $node->text();
        });

        if(!empty($result)) {
            return $result[0];
        }

        return '';
    }

Mình đã chọc vào từng link và xử lý bằng hàm scrapedata, logic của scrapedata, handle thì tương tự nhau và mình cũng đã hướng dẫn từ đầu. Ở cuối mình có lưu vào database.

Cuối cùng bạn chạy lại lệnh:

php artisan scrape:post

Vậy là bạn đã có thể crawler data từ một trang web nào đó rồi. Các bạn sự dụng data với mục định test hoặc nghiên cứu thôi nhé.

Laravel Crawler Data cực kì đơn giản với Goutte

Kết luận

Việc crawler data trở nên đơn giản hơn với Goutte. Bạn có thể tham khảo thêm về Goutte tại đây: https://github.com/FriendsOfPHP/Goutte
Nhưng việc sử dụng Goutte vẫn còn nhiều hạn chế. Việc scrape data chỉ dùng lại ở trang đầu. Để xử lý được, cần dùng một browser simulator như puppeteer của Javascript. Nội dung về puppeteer có thể sẽ được thảo luận ở một bài viết trong tương lai.

Tài liệu tham khảo

  • https://github.com/FriendsOfPHP/Goutte
  • https://blog.pirago.vn/laravel/?fbclid=IwAR0fX8BH8FTsQ6y3THlidMsRxP_Ya_-2osLaLkSvyiMnlZDN1Vyb3JcGluA
  • https://viblo.asia/p/crawl-data-bang-laravel-va-goutte-L4x5x3ewlBM#_ket-luan-10

Nguồn : https://blog.haposoft.com

0 0 đánh giá
Article Rating
Theo dõi
Đăng nhập
Thông báo của
guest
guest
0 Comments
Cũ nhất
Mới nhất Được bỏ phiếu nhiều nhất
Phản hồi nội tuyến
Xem tất cả bình luận

Sidebar chính

LỜI NGỎ

Đây là blog cá nhân, cung cấp các thông tin, kiến thức và kinh nghiệm về lập trình và cuộc sống. Những bài viết được mình sưu tập từ nhiều nguồn, mọi chi tiết liên quan đến bản quyền xin vui lòng liên hệ qua email kairu2607@gmail.com ! Cám ơn rất nhiều.

Tìm kiếm

Thủ thuật Wordpress

T

Tạo trang chuyển hướng download cho WordPress

[flatsome ] Text Ticker (fade) For Top Bar In Flatsome Theme

[Flatsome] Text Ticker (Fade) for Top Bar in Flatsome Theme

Định Dạng ảnh Webp Là Gì ? Làm Thế Nào để Sử Dụng Webp Trên Wordpress 2024 Mới Nhất ?

Định dạng ảnh WebP là gì ? Làm thế nào để sử dụng WebP trên WordPress 2024 mới nhất ?

X

Xử Lý Lỗi Không Xem Được Giỏ Hàng Và Thanh Toán Woocommerce Website WordPress

Vì Sao Rank Math Vượt Trội – SEO WordPress 2023

Hướng Dẫn Ghi đè (override) Folder Inc Trong Child Theme Flatsome

Hướng dẫn ghi đè (override) folder INC trong child-theme Flatsome

Hướng Dẫn Quản Lý Trang Trong Website WordPress

Laravel

Một số câu hỏi câu hỏi phổ biến phỏng vấn tuyển dụng lập trình viên Laravel

Thiết kế cấu trúc folder HMVC cho Laravel

Tại sao lại sử dụng Laravel Service và Repository Pattern?

[Laravel 7] Tổ chức theo dạng Package/Module trong ứng dụng Laravel – P3: khai báo config, translation, helpers và migrations

[Laravel 7] Tổ chức theo dạng Package/Module trong ứng dụng Laravel – P2: Route và mô hình MVC

[Laravel 7] Tổ chức theo dạng Package/Module trong ứng dụng Laravel – P1: Giới thiệu và khởi tạo cấu trúc thư mục cơ bản

Codeigniter Framework

[CodeIgniter 4] Codeigniter 4 Remove Public and Index.php From URL

[CodeIgniter 4] How to upload Codeigniter 4 website on share hosting?

Sửa lỗi website Codeigniter 2.x không chạy được với PHP 7.x

[CodeIgniter 4] Sử dụng cURL trong CodeIgniter 4

[CodeIgniter 4] Sử dụng cache để tăng tốc website trong CodeIgniter 4

[CodeIgniter 4] Xử lý hình ảnh chuyên nghiệp trong CodeIgniter 4

[CodeIgniter 4] Hướng dẫn gửi mail trong CodeIgniter 4

Dịch vụ Thiết Kế Website

Phần mềm hay

Hướng dẫn chuyển đổi php version trong ~/.zshrc ở MacOs

Tim Hieu Ve He Dieu Hanh Macos 1

Sửa file Hosts trong hệ điều hành MacOS

Hướng dẫn sử dụng phần mềm putty trên Windows

Switching between multiple PHP versions on macOS

Byebye Edge Chromium/Microsoft Edge

Copyright © 2025 · Metro Pro on Genesis Framework · WordPress · Đăng nhập

wpDiscuz