phan / phan/phan

`$users->count() > 0` does not imply `$users->first()` is non-null: $PhanTypeExpectedObjectPropAccess reported on Laravel collection items

Open
#4,723 4 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

question working as intended
Dominant language
PHP
Stars
5.6k
Forks
365
Avg merge
1h 25m
Merged PRs (30d)
6

Description

Hi

I'm getting a weird error when fetching first element of a collection (constructed from an eloquent db model):

        $users = User::all();
        if ($user->count() > 0) {
            // @var User $user
            $user = $users->first();
            return $user->id;
        }

The error I get:

PhanTypeExpectedObjectPropAccess Expected an object instance when accessing an instance property, but saw an expression $user with type TValue|null

The @var annotation doesn't make a change...
The only thing that works is asserting (locally) the variable like this:

        $users = User::all();
        if ($user->count() > 0) {
            // @var User $user
            $user = $users->first();
            if (null === $user) {
                throw new \Exception('user is null, it should not');
            } else if (!$user instanceof User) {
                throw new \Exception('$user should be an instance of User');
            }
            return $user->id;
        }

I also tried to externalize the logic in another class to make the code shorter but it not preventing the phan error reporting ...

        $users = User::all();
        if ($user->count() > 0) {
            // @var User $user
            $user = $users->first();
            // throws an exception if variable is null or if not an instance of the provided class
            TypeAssertion::assert($user, User::class);

            return $user->id;
        }

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

The issue names no source file or test; start by reproducing the Laravel collection example and tracing the PhanTypeExpectedObjectPropAccess diagnostic. Verify how count() and first() are modeled, then add coverage for the reported non-null implication while preserving diagnostics for genuinely nullable values.

Written by the indexing model from the issue text.

Assessment

Tech stack
laravel, php
Domain
devtools
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.