Surzhikov
@Surzhikov
Разработчик

Как сделать кеширование свойств модели Eloquent?

Добрый день.
Есть модель, в ней есть связь hasMany и есть несколько геттеров для получения количества связей.

Придуманный простой пример:

class Group extends Model
{

.....

public function Users()
{
	return $this->hasMany(User::class);
}

/**
 * Геттер количества активных пользователей
 */
public function getUsersActiveCountAttribute()
{
	return $this->Users()->where('status', '=', 'active')->count();
}

/**
 * Геттер количества заблокированных пользователей
 */
public function getUsersBlockedCountAttribute()
{
	return $this->Users()->where('status', '=', 'blocked')->count();
}

}


Я хочу выводить в blade количество юзеров, если оно не 0;

@if($City->users_active_count > 0)
Количество активных: {{$City->users_active_count}}
@endif

@if($City->users_blocked_count > 0)
Количество заблокированных: {{$City->users_blocked_count}}
@endif


Получается что запрос к БД выполняется дважды (при проверке и при выводе). Это плохо.
Вопрос, как сделать максимально элегантный вариант как этого избежать?
  • Вопрос задан
  • 133 просмотра
Решения вопроса 1
@Kostik_1993
Web Developer
вы неправильно решаете вашу задачу и не читаете доки - это ваша самая грубая ошибка

Можно оптимизировать код и запросы двумя способами
Первый:
для геттеров получать информацию из коллекции, а не из базы
public function getUsersActiveCountAttribute()
{
  return $this->Users->where('status', '=', 'active')->count();
}


Второй:
Брать данные из базы предварительно их загрузив
public function UsersActive()
{
  return $this->hasMany(User::class)->where('status', '=', 'active');
}


В контроллере не забудьте эти данные подгрузить
Для первого
$goups = Group::with('Users')->get();

Для второго
$goups = Group::withCount(['UsersActive'])->get();
Когда ты получаешь вторым способом то для каждой группы у тебя будет доступно свойство
$group->users_active_count

Советую вам сначала вдумчиво и несколько раз почитать доку
Ответ написан
Пригласить эксперта
Ответы на вопрос 1
@Arik
Так случайно не умеет блэйд?
@if(($t = $City->users_active_count) > 0)
Количество активных: {{$t}}
@endif
Ответ написан
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы