Matthew Malone
Matthew Malone

Reputation: 473

Laravel 5 whereHas chaining and orWhere

Trying to query a model with a lower level relationship (agreement) and I cannot get chaining to work. I tried the three methods below (the second get me 99% of the way there, but it misses out on one of the results - an inactive equipment "status" and an "inactive" agreement (should have been omitted). What am I doing wrong?

Every piece of equipment needs to be "active" and have an active existing agreement (an active agreement is one that is either "Active", "Cancel on expiry" or "Unsigned").

    $thing = Equipment::wherehas('agreement', function($q)use($month)
    {
        $q->where('equipment.status', '=', 'Active')
          ->where('maintenance_months', 'like', '%'.$month.'%')
          ->where('status', '=', 'Active')
          ->orWhere('status', '=', 'Unsigned')
          ->orWhere('status', '=', 'Cancel on expiry');
    })->Get();

    $thing = Equipment::wherehas('agreement', function($q)use($month)
    {
        $q->where('status', '=', 'Active')
          ->orWhere(function($q2)use($month)
          {
                $q2->where('equipment.status', '=', 'Active')
                   ->where('maintenance_months', 'like', '%'.$month.'%');
          })
          ->where('status', '=', 'Unsigned')
          ->orWhere(function($q3)use($month)
          {
                $q3->where('equipment.status', '=', 'Active')
                   ->where('maintenance_months', 'like', '%'.$month.'%');
          })
          ->where('status', '=', 'Cancel on expiry')
          ->orWhere(function($q4)use($month)
          {
                $q4->where('equipment.status', '=', 'Active')
                   ->where('maintenance_months', 'like', '%'.$month.'%');
          });
    })->Get();      

    $thing = Equipment::wherehas('agreement', function($q)use($month)
    {
        $q->where('status', '=', 'Active')
          ->where('equipment.status', '=', 'Active')
          ->where('maintenance_months', 'like', '%'.$month.'%')
          ->orWhere('status', '=', 'Unsigned')
          ->where('equipment.status', '=', 'Active')
          ->where('maintenance_months', 'like', '%'.$month.'%')
          ->orWhere('status', '=', 'Cancel on expiry')
          ->where('equipment.status', '=', 'Active')
          ->where('maintenance_months', 'like', '%'.$month.'%');
    })->get();

Upvotes: 0

Views: 1762

Answers (1)

terry low
terry low

Reputation: 10618

i am not quite understand why the where equipment.status is being filter for the same thing over and over again, if i am not understand wrongly the following code might be the result you are looking for.

$thing = Equipment::whereHas('agreement', function($q)use($month)
{
    $q->where('maintenance_months', 'like', '%'.$month.'%')
      ->whereIn('status',['Unsigned','Active','Cancel on Expiry'])
})->where('status','Active')->get();

Upvotes: 3

Related Questions