Skip to content

Relational queries populating invalid models when foreign key / linking value is 0 #20117

Open
@BVBAccelm

Description

@BVBAccelm

Yii's functionality to join / populate relations on a model doesn't work properly in circumstances where the foreign key (linking value) is a 0. The issue stems from here ( https://github.com/yiisoft/yii2/blob/master/framework/db/ActiveRelationTrait.php#L314 ). The getModelKey can return false when there is no value. The line in question:

$value = isset($buckets[$key]) ? $buckets[$key] : ($this->multiple ? [] : null);

will return an item in that array with index 0 ($buckets[false] === $buckets[0]) instead of null which it should.

What steps will reproduce the problem?

Create two database tables, user and person. Table user has id, and email. Table person has user_id and name where user_id is not a required field.

Create the active record models and relations for them, populate a dozen records into each table, making sure that the user table has a record with id value 0. Make sure one record in the person table has user_id 0, and make several of those records have user_id as null.

Using an Active Query perform one like:

$models = Person::find()->with(['user'])->all();

What is the expected result?

All Person models that have user_id as null should not have a related model populated for the user relation.

What do you get instead?

All Person models that have user_id as null end up having the user record with id 0 populated.

Additional info

Not really sure the best way to handle this. Everything I've checked ends up having $arr[false] === $arr[0]. So I'm not sure how you can differentiate one from the other. Maybe this line:

$value = isset($buckets[$key]) ? $buckets[$key] : ($this->multiple ? [] : null);

Should become:

$value = $key !== false && isset($buckets[$key]) ? $buckets[$key] : ($this->multiple ? [] : null);

but I'm honestly not sure if that has unwanted side effects. I can't imagine a scenario where someone would have a value indexed with false, but maybe someone more involved with the project would.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions