Laravel Eloquent Macros

Ever need to use a methodology not available in eloquent, and need to use it across a few different Models

in Laravel, PHP, Tips & Tricks

Been there done that.

Your first though may be - why not just plug in a trait? while that works lets consider its not the best solution out there.

Lets consider the following scenario. You are busy migrating code from an older system to Laravel, and you need to query on a few tables / columns where the column could either be null or an empty. string or an 0.

so you create a scope:

public function scopeWhereNullZeroOrEmpty(Builder $builder, $column)
{
	return $builder->where(function(Builder $builder) use ($column)  {
		$builder->whereNull($column)
		->orWhere($column, '')
		->orWhere($column, 0);
	}

}

Now you can plug that in on all your queries and it works, implement as a trait on each model where you may need it.

Another approach, one which i prefer, is to make use of Laravel Macros to extend and allow yo a new method

in your AppServiceProvider.php add to the register method as follows

Builder::macro('whereNullZeroOrEmpty', function (string $column) {
    return $this->where(function (Builder $builder) use ($column) {
        $builder->whereNull($column)
		->orWhere($column, '')
		->orWhere($column, 0);
     });
}

As you can see the code is pretty much identical, the difference comes in now, that you do not need to add this trait to any of your models in order to use it.

both methods would be called:

Mymodel::whereNullZeroOrEmpty('xxxx')->get();

Now another advantage of the macro option is that you could create yourself a little helper package and include this and your other ones in a package, and on the next project simply install it via composer.