[Laravel] Có nên truy vấn database trong boot() ❌
$data = Cache::remember($configKey, 3600, function () use ($configKey) {
Log::info('Query settings table executed in AppServiceProvider');
$setting = DB::table('settings')->where('code', $configKey)->first();
return $setting ? json_decode($setting->json, true) : $this->defaultSettings();
});
PHPRủi ro
- Service providers được chạy trong mọi request và cả khi chạy lệnh Artisan (
php artisan queue:work
,php artisan migrate
,php artisan config:cache
, v.v.). - Nếu cache hết hạn hoặc chưa tồn tại, nó sẽ truy vấn database ngay khi ứng dụng khởi động, có thể gây chậm ứng dụng hoặc lỗi khi không có database (trong quá trình cài đặt).
- Nếu database chưa được thiết lập hoặc bảng
settings
chưa tồn tại, có thể gây lỗi “Base table or view not found”.
Cách khắc phục ✅
Tránh truy vấn database trực tiếp trong boot()
, thay vào đó chỉ nên gọi nó khi thực sự cần:
if (Schema::hasTable('settings')) { // Kiểm tra bảng có tồn tại không trước khi truy vấn
$data = Cache::rememberForever($configKey, function () use ($configKey) {
Log::info('Query settings table executed in AppServiceProvider');
$setting = DB::table('settings')->where('code', $configKey)->first();
return $setting ? json_decode($setting->json, true) : [];
});
Config::set($configKey, $data);
}
PHP🔹 Sử dụng Schema::hasTable('settings')
để tránh lỗi khi database chưa sẵn sàng.
🔹 Đổi 3600
thành rememberForever()
nếu dữ liệu hiếm khi thay đổi để giảm truy vấn database.