Skip to content

[Bug] Querying relations with extra conditions not working as expected #1272

Closed
@NoelDeMartin

Description

@NoelDeMartin

I have been some time playing with the querying system for eloquent to get something done, and recently I found something that I think is a bug.

I have a table "Teams", with id and name columns. And I have a table "Matches" with local_id and visitant_id. What I want to achieve is to get all the matches a team has played, be it as local or visitant. And finally I come up with this.

On the Teams model:

class Team extends Eloquent {
    public function matches_as_visitant() {
        return $this->hasMany('Match', 'visitant_id');
    }
}

On the Teams controller:

$team = Team::with(['matches_as_visitant' => function($query) {
            $query->orWhere('local_id', '=', '2');
            $query->orderBy('local_id', 'asc');
        }])->find(2);

The query that is run with this is:

select * from `matches` where `matches`.`visitant_id` in (?) or `local_id` = ? order by `local_id` asc

After this I expect $team->matches_as_visitant to be actually all the matches, because the eloquent model already matches the visitant_id field and I add a orWhere part where it checks for the local_id. This should work but doesn't, I've been inspecting the framework code and I found at which point this actually "stops working".

In the HasOneOrMany class we have a method matchOneOrMany:

protected function matchOneOrMany(array $models, Collection $results, $relation, $type)
{
    $dictionary = $this->buildDictionary($results);

    // Once we have the dictionary we can simply spin through the parent models to
    // link them up with their children using the keyed dictionary to make the
    // matching very convenient and easy work. Then we'll just return them.
    foreach ($models as $model)
    {
        $key = $model->getKey();

        if (isset($dictionary[$key]))
        {
            $value = $this->getRelationValue($dictionary, $key, $type);

            $model->setRelation($relation, $value);
        }
    }

    return $models;
}

Basically the $results variable is a Collection with all the matches, but then the $models variable (that is then returned) only contains the matches played as visitant, and the local matches are lost.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions