Factory là thư viện để tạo ra các dữ liệu mẫu 1 cách tự động và nhanh chóng. factory làm việc kết hợp với model và các thành phần seeder và migrate trong laravel tạo thành 1 bộ công cụ hữu ích cho các nhà phát triển backend. Trong bài viết này tôi sẽ hướng dẫn chi tiết cách sử dụng công cụ factory này.
Để thực hiện được factory dữ liệu chúng ta cần tạo migrations trước để tạo ra bảng dữ liệu. Trong bài hướng dẫn này tôi sử dụng bảng users để factory dữ liệu nên tôi không caanfh tạo migrations nữa, vì bảng users mặc định khi cài đặt thì laravel đã tự động tạo cho chúng ta, tuy nhiên thì các trường dữ liệu chúng ta cần thêm vào cho đầy đủ. Chúng ta tiến hành thêm cột avatar và cột slug như sau.
mở file migrations của bạn trong thư mục database/migrations sửa đoạn code như hình dưới
Sau đó chúng ta chạy lệnh sau để tạo bảng dữ liệu
php artisan migrate
Nếu như bạn đã chạy lệnh migrate trước đó thì bạn có thể chạy lệnh sau để reset lại bảng dữ liệu
php artisan migrate:refresh
Nếu chạy thành công thì ta sẽ thấy thông báo như sau ở terninal
Chúng ta có thể kiểm tra kết qua trong database
Như vậy tôi đã tạo được bảng dữ liệu users đồng thời thêm 2 cột là avatar và slug. Trong thực tế các dự án thì chúng ta cũng có thể sẽ gặp trường hợp cần thêm nhiều trường dữ liệu khác nữa thì chúng ta cũng thực hiện tương tự như thêm 2 trường này.
Để tạo factory ta chạy lệnh sau
php artisan make:factory nameFactory
Ở đây tôi có một lưu ý dành cho bạn là tên của factory bắt buộc phải có Factory ở phía sau như trong câu lệnh trên, nếu như bạn để mỗi name thì lệnh chạy sẽ bị lỗi. Trong trường hợp này tôi đang thao tác với bản users nên laravel đã tạo sẵn cho tôi file factory rồi nên không phải tạo nữa, sau này cần thực hiện với các bảng dữ liệu khác thì bạn cần phải tự tạo ra file này bằng câu lệnh ở trên.
Bạn vào database/factories và mở file facory của mình lên. ở hình trên laravel đã tự tạo sẵn cho chúng ta các trường cơ bản. bây giờ cùng ta thêm trường avatar và trường slug như sau
Ở trên tôi đã khai báo thêm $name và dùng biến name để tạo ra chuỗi slug dùng hàm Str. đồng thời tạo ra các thư lục trong public như hình trên. trong thư mục /upload/files/users tôi tải 1 số hình ảnh để làm avatar, khi chạy factory thì laravel sẽ tự động lấy các hình ảnh trong mục này để làm avatar và copy nó sang mục /upload/image/users đồng thời ganarate tên file. khai báo false ở hàm factory file để chỉ trả về tên file. nếu để true thì hàm sẽ trả về fullpath của file trên máy tính, như vậy thì khi xử lý login link ảnh sẽ bị sai.
Chúng ta tải 1 số hình ảnh vào thư mục nguồn đã khai báo để làm avatar.
Để tạo seeder chúng ta chạy lệnh sau
php artisan make:seeder UserSeeder
Trong trường hợp này tôi đặt tên là UserSeeder. File seeder được tạo ra trong thư mục database/seeder
Lưu ý rằng trong thư mục seeder có file tên là DatabseSeeder.php file này là file chạy chính của seeder, sau khi ta khai báo các fie seeder của các bảng dữ liệu thì chúng ta phải gọi file seeder của các bảng muốn chạy seeder trong file này. Nếu chúng ta không gọi trong file này thì dữ liệu của bảng đó sẽ không được seed.
Ở file UserSeeder vừa tạo tôi sẽ use model vào và gọi hàm factory như hình, hàm count chúng ta truyền vào số bản ghi cần tạo. để sử dụng được hàm factory thì trong model chúng ta có nhúng thư viện factory như hình sau.
Việc nhúng thư viện factory trong model thì laravel đã tự động nhúng cho chúng ta rồi, chúng ta chỉ việc sử dụng nó thôi.
Bạn mở file DatabaseSeeder.php trong thư mục database/seeder lên và thêm dòng call đến UserSeeder như hình dưới.
Tiếp theo chúng ta chạy lệnh sau
php artisan db:seed
Chúng ta được kết quả như sau
Chúng ta kiểm tra dữ liệu trong database
Chúng ta thử lấy 1 đường link ở cột avatar nối với chuối localhost:8000 xem hình ảnh có hiển thị hay không
Như vậy là việc factory ảnh avatar chúng ta đã thành công.
Như vậy là trên đây tôi đã hướng dẫn chi tiết cách để chúng ta tạo ra dữ liệu mẫu hoàn toàn tự động, trong đó có sử dụng những hình ảnh của chúng ta để random ra avatar cho các bản ghi. Việc factory này có thể sẽ rất cần thiết để chúng ta triển khai các dự án backend cung cấp API cho các ứng dụng fontend, chúng ta dùng để tạo dữ liệu mẫu và test các chức năng khi phát triển hệ thống. Chúc bạn sẽ thực hiện thành công.
Phần 2:
Factory và Seeder trong Laravel là những công cụ vô cùng mạnh mẽ giúp bạn tạo ra dữ liệu mẫu một cách nhanh chóng và tự động. Việc này đặc biệt hữu ích khi phát triển các dự án backend, kiểm thử API, hoặc đơn giản là có dữ liệu để phát triển giao diện người dùng. Bài viết này sẽ hướng dẫn bạn từng bước cách tạo dữ liệu mẫu, bao gồm cả việc random ảnh avatar, để bạn có thể áp dụng vào dự án của mình một cách hiệu quả nhất.
Để tạo dữ liệu mẫu, bước đầu tiên và quan trọng nhất là phải có một bảng dữ liệu. Trong Laravel, Migrations đóng vai trò thiết yếu trong việc quản lý cấu trúc cơ sở dữ liệu.
Mặc định, Laravel đã cung cấp sẵn bảng users
khi bạn cài đặt. Tuy nhiên, để đáp ứng nhu cầu thực tế của việc factory dữ liệu với các trường tùy chỉnh như ảnh đại diện và slug, chúng ta cần bổ sung thêm các cột này vào bảng users
.
Các bước thực hiện:
database/migrations
và mở file migration của bảng users
(thường có tên dạng YYYY_MM_DD_HHMMSS_create_users_table.php
).avatar
và slug
: Thêm đoạn mã sau vào phương thức up()
của file migration:
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Run the migrations.
*/
public function up(): void
{
Schema::create('users', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->string('email')->unique();
$table->timestamp('email_verified_at')->nullable();
$table->string('password');
// Thêm hai cột mới: avatar và slug
$table->string('avatar')->nullable(); // Cột avatar, cho phép null
$table->string('slug')->unique(); // Cột slug, phải là duy nhất
$table->rememberToken();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*/
public function down(): void
{
Schema::dropIfExists('users');
}
};
Lưu ý: Cột avatar
được khai báo là nullable()
vì có thể người dùng chưa có ảnh đại diện ngay. Cột slug
được khai báo là unique()
để đảm bảo tính duy nhất cho mỗi người dùng, phục vụ cho các URL thân thiện.
[CHÈN HÌNH ẢNH MINH HỌA 1: Code thêm cột avatar và slug vào migration]
Chú thích ảnh: Thêm cột avatar
và slug
vào file migration của bảng users.
php artisan migrate
php artisan migrate:refresh
Sau khi chạy thành công, bạn sẽ thấy thông báo tương ứng trên Terminal và có thể kiểm tra kết quả trong cơ sở dữ liệu của mình. Bảng users
giờ đây đã có thêm hai cột avatar
và slug
.
[CHÈN HÌNH ẢNH MINH HỌA 2: Thông báo chạy lệnh migrate:refresh thành công trên terminal]
Chú thích ảnh: Thông báo khi chạy lệnh php artisan migrate:refresh
thành công.
[CHÈN HÌNH ẢNH MINH HỌA 3: Kiểm tra trong database sau khi migrate]
Chú thích ảnh: Bảng users trong cơ sở dữ liệu sau khi thêm cột avatar
và slug
.
Factory là nơi bạn định nghĩa các khuôn mẫu dữ liệu cho từng model. Đây là "trái tim" của quá trình tạo dữ liệu mẫu, nơi bạn khai báo các quy tắc để generate (tạo ngẫu nhiên) giá trị cho từng trường dữ liệu.
Các bước thực hiện:
UserFactory.php
cho bảng users
. Tuy nhiên, nếu bạn làm việc với các bảng khác, bạn cần tạo factory mới bằng lệnh:
php artisan make:factory TênModelFactory
Lưu ý quan trọng: Tên của factory bắt buộc phải có hậu tố Factory
(ví dụ: PostFactory
, ProductFactory
). Nếu không, lệnh sẽ báo lỗi.
[CHÈN HÌNH ẢNH MINH HỌA 4: Cấu trúc file factory mặc định]
Chú thích ảnh: Cấu trúc file factory mặc định của Laravel.
database/factories
và mở file UserFactory.php
. Laravel đã cung cấp sẵn các trường cơ bản. Giờ chúng ta sẽ thêm logic cho các trường avatar
và slug
.
<?php
namespace Database\Factories;
use App\Models\User; // Đảm bảo đã import User model
use Illuminate\Database\Eloquent\Factories\Factory;
use Illuminate\Support\Str; // Import Str facade để xử lý chuỗi slug
class UserFactory extends Factory
{
/**
* The name of the factory's corresponding model.
*
* @var string
*/
protected $model = User::class;
/**
* Define the model's default state.
*
* @return array
*/
public function definition()
{
// Tạo một biến $name để sử dụng cho cả name và slug
$name = $this->faker->name();
// Đường dẫn thư mục nguồn chứa ảnh avatar
// Đảm bảo bạn đã tạo thư mục này và tải ảnh vào
$source_path = public_path('upload/files/users');
// Đường dẫn thư mục đích nơi ảnh sẽ được copy đến
$destination_path = public_path('upload/image/users');
// Tạo thư mục đích nếu chưa tồn tại
if (!file_exists($destination_path)) {
mkdir($destination_path, 0777, true);
}
return [
'name' => $name,
'email' => $this->faker->unique()->safeEmail(),
'email_verified_at' => now(),
'password' => '$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi', // password
'remember_token' => Str::random(10),
// Tạo slug từ tên người dùng
'slug' => Str::slug($name),
// Chọn ngẫu nhiên một ảnh từ thư mục nguồn và copy sang thư mục đích
// Sau đó chỉ trả về tên file để lưu vào database
'avatar' => $this->faker->image($source_path, 640, 480, null, false, true, null, false, $destination_path)
];
}
}
Giải thích chi tiết các thành phần:
use Illuminate\Support\Str;
: Import Str
facade để dễ dàng tạo slug từ chuỗi tên người dùng.$name = $this->faker->name();
: Sử dụng thư viện faker
để tạo tên ngẫu nhiên. Biến $name
này sẽ được dùng để tạo cả trường name
và slug
.$source_path
: Đường dẫn đến thư mục chứa các ảnh gốc mà bạn muốn sử dụng làm avatar. Bạn cần tạo thư mục này (ví dụ: public/upload/files/users
) và tải một vài ảnh vào đó.$destination_path
: Đường dẫn đến thư mục mà ảnh avatar đã được chọn ngẫu nhiên sẽ được copy đến. (ví dụ: public/upload/image/users
).if (!file_exists($destination_path)) { mkdir($destination_path, 0777, true); }
: Đảm bảo thư mục đích tồn tại. Nếu chưa, nó sẽ được tạo tự động với quyền ghi.$this->faker->image(...)
: Đây là hàm quan trọng để tạo ảnh.
$source_path
): Thư mục nguồn chứa ảnh.640, 480
): Kích thước ảnh (chiều rộng, chiều cao).false
: Quan trọng! Tham số này đảm bảo hàm chỉ trả về tên file (ví dụ: abc.jpg
) chứ không phải đường dẫn đầy đủ trên hệ thống. Điều này giúp tránh lỗi đường dẫn khi hiển thị ảnh trên frontend.$destination_path
: Xác định thư mục đích để copy ảnh.[CHÈN HÌNH ẢNH MINH HỌA 5: Code factory thêm trường avatar và slug]
Chú thích ảnh: Thêm logic tạo dữ liệu cho các trường avatar
và slug
trong UserFactory
.
[CHÈN HÌNH ẢNH MINH HỌA 6: Cấu trúc thư mục upload/files/users]
Chú thích ảnh: Cấu trúc thư mục public/upload/files/users
nơi chứa ảnh gốc cho avatar.
Sau khi đã có Factory định nghĩa cách tạo dữ liệu, chúng ta cần một Seeder để "kích hoạt" Factory và đưa dữ liệu vào cơ sở dữ liệu.
Các bước thực hiện:
users
:
php artisan make:seeder UserSeeder
File UserSeeder.php
sẽ được tạo trong thư mục database/seeders
.
[CHÈN HÌNH ẢNH MINH HỌA 7: File UserSeeder được tạo]
Chú thích ảnh: File UserSeeder.php
sau khi được tạo.
UserSeeder.php
và thêm đoạn mã sau vào phương thức run()
:
<?php
namespace Database\Seeders;
use Illuminate\Database\Seeder;
use App\Models\User; // Đảm bảo đã import User model
class UserSeeder extends Seeder
{
/**
* Run the database seeds.
*
* @return void
*/
public function run()
{
// Gọi factory của User model và tạo 100 bản ghi
User::factory()->count(100)->create();
}
}
use App\Models\User;
: Import User
model để có thể sử dụng factory()
method.User::factory()->count(100)->create();
: Dòng này sẽ gọi factory của User
model, yêu cầu tạo 100 bản ghi dữ liệu và lưu chúng vào cơ sở dữ liệu. Bạn có thể thay đổi số lượng bản ghi tùy theo nhu cầu.[CHÈN HÌNH ẢNH MINH HỌA 8: Code trong UserSeeder]
Chú thích ảnh: Code trong UserSeeder.php
để gọi User Factory và tạo bản ghi.
factory()
trực tiếp từ model (User::factory()
), model của bạn cần sử dụng trait HasFactory
. Laravel thường tự động thêm trait này khi bạn tạo model mới. Bạn có thể kiểm tra trong file app/Models/User.php
:
<?php
namespace App\Models;
use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Database\Eloquent\Factories\HasFactory; // Đảm bảo trait này có
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;
use Laravel\Sanctum\HasApiTokens;
class User extends Authenticatable
{
use HasApiTokens, HasFactory, Notifiable; // Đảm bảo HasFactory có mặt
// ... các thuộc tính khác của model
}
[CHÈN HÌNH ẢNH MINH HỌA 9: Trait HasFactory trong User Model]
Chú thích ảnh: Đảm bảo HasFactory
trait được sử dụng trong User
Model.
DatabaseSeeder.php
(trong thư mục database/seeders
). Đây là nơi bạn "gọi" các seeder con của mình để chúng được chạy khi lệnh db:seed
được thực thi.
Mở file DatabaseSeeder.php
và thêm dòng gọi UserSeeder
vào phương thức run()
:
<?php
namespace Database\Seeders;
use Illuminate\Database\Seeder;
class DatabaseSeeder extends Seeder
{
/**
* Seed the application's database.
*
* @return void
*/
public function run()
{
// Gọi UserSeeder để seed dữ liệu cho bảng users
$this->call(UserSeeder::class);
// Nếu có các seeder khác, bạn cũng gọi tương tự
// $this->call(ProductSeeder::class);
}
}
[CHÈN HÌNH ẢNH MINH HỌA 10: Gọi UserSeeder trong DatabaseSeeder]
Chú thích ảnh: Gọi UserSeeder
trong file DatabaseSeeder.php
.
Sau khi đã hoàn tất việc cấu hình Factory và Seeder, giờ là lúc chạy lệnh để đưa dữ liệu mẫu vào cơ sở dữ liệu của bạn.
Các bước thực hiện:
php artisan db:seed
users
. Bạn sẽ thấy số lượng bản ghi mà bạn đã định nghĩa trong UserSeeder
(ví dụ: 100 bản ghi) đã được tạo ra với dữ liệu ngẫu nhiên, bao gồm cả avatar
và slug
.
[CHÈN HÌNH ẢNH MINH HỌA 11: Thông báo chạy lệnh db:seed thành công]
Chú thích ảnh: Kết quả khi chạy lệnh php artisan db:seed
thành công.
[CHÈN HÌNH ẢNH MINH HỌA 12: Dữ liệu đã được seed trong database]
Chú thích ảnh: Dữ liệu mẫu đã được tạo trong bảng users
của cơ sở dữ liệu.
Bạn có thể thử lấy một đường dẫn avatar
từ cột avatar
và nối nó với địa chỉ localhost:8000
(hoặc domain của bạn) để kiểm tra xem ảnh có hiển thị đúng không.
Ví dụ: Nếu cột avatar
chứa upload/image/users/ten_file_anh.jpg
, bạn sẽ truy cập: http://localhost:8000/upload/image/users/ten_file_anh.jpg
.
[CHÈN HÌNH ẢNH MINH HỌA 13: Kiểm tra đường link avatar có hiển thị ảnh]
Chú thích ảnh: Kiểm tra đường dẫn ảnh avatar có hiển thị hình ảnh đúng.
Việc thành thạo cách sử dụng Factory và Seeder trong Laravel là một kỹ năng quan trọng giúp bạn tăng tốc độ phát triển dự án. Bạn đã biết cách:
Kỹ thuật này đặc biệt hữu ích cho:
Chúc mừng bạn đã hoàn thành hướng dẫn này! Hãy tiếp tục khám phá và áp dụng những kiến thức này vào các dự án Laravel của mình để tối ưu hóa quy trình phát triển.