Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add generic hints to Cache #45325

Closed
wants to merge 1 commit into from
Closed

Add generic hints to Cache #45325

wants to merge 1 commit into from

Conversation

AJenbo
Copy link
Contributor

@AJenbo AJenbo commented Dec 15, 2022

This provides a way for IDEs and other analyzer tools to reason about the value returned by the cache and there by not cause lose of context when ever it is used. See #38257 for a general discussions about this topic.

This PR is opened against master as generic annotations on the cache component is meant to come after 9.x.

P.s. @nunomaduro could you please share some more information regarding the plans for introducing generic annotations on the framework as it would make it easier to work on :)

@driesvints
Copy link
Member

Can't this be sent to 9.x instead?

@AJenbo
Copy link
Contributor Author

AJenbo commented Dec 15, 2022

Can't this be sent to 9.x instead?

I was told it coudn't

@driesvints
Copy link
Member

Who did? @nunomaduro just said that we can't add these in general:

#40759 (comment)

It's been over a year so maybe we can reconsider but it's up to @taylorotwell to decide.

@AJenbo
Copy link
Contributor Author

AJenbo commented Dec 15, 2022

Ok, I'm not privy to what the reasoning is. But I'm happy to have it go in 9.x if possible.

@nunomaduro just said that we can't add these in general:

They where added for other components so it felt specific for the cache component?

P.s. I'm pretty sure it's still 2022, or I forgot to show up for xmas which would be pretty bad :D

@axlon
Copy link
Contributor

axlon commented Dec 15, 2022

These seem wrong to me, just because we pass a default doesn't mean that the value in the cache is of that type as well:

cache()->put('foo', 'bar');
cache()->get('foo', 123);

This will return a string but according to this PR it will return an int.

@taylorotwell
Copy link
Member

Thanks for sending this in. I'm going to mark it as draft for now while people discuss it and also while we wait for @nunomaduro to return from vacation.

@taylorotwell taylorotwell marked this pull request as draft December 15, 2022 15:14
@AJenbo
Copy link
Contributor Author

AJenbo commented Dec 15, 2022

These seem wrong to me, just because we pass a default doesn't mean that the value in the cache is of that type as well:

cache()->put('foo', 'bar');
cache()->get('foo', 123);

This will return a string but according to this PR it will return an int.

I guess this is true, thought this feels like somewhat dubious usage.

The same issue could technically also occur with remember():

cache()->remember('foo', 60, function (): string { return 'bar'});
cache()->remember('foo', 60, function (): int { return 123});

For such cases I think it would be fair to still warn the user that they are likely doing something wrong.

Copy link
Member

@nunomaduro nunomaduro left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've made some comments that must be addressed before merging. Also, can you rebase this on v9.x please?

@@ -175,9 +177,11 @@ protected function handleManyResult($keys, $key, $value)
/**
* Retrieve an item from the cache and delete it.
*
* @template TCached of mixed
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please use TCacheValue everywhere, and remove of mixed.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh neat I wasn't aware of that short hand

* @param mixed $default
* @return mixed
* @param TCached $default
* @return null|TCached
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No need for null here.

* @param string $key
* @param mixed $default
* @return mixed
* @param TCached $default
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should consideration that the $default value may be a closure that returns TCacheValue. And this comment can applied to other arguments annotations in this pull request.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wasn't aware of this possibility in Laravel, hopefully this will help more discover it as well :)

@@ -0,0 +1,28 @@
<?php
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You will need to add tests for the cases when a closure is given for the $default arguments.

@AJenbo
Copy link
Contributor Author

AJenbo commented Dec 20, 2022

I've made some comments that must be addressed before merging. Also, can you rebase this on v9.x please?

Thanks! I'll look in to it 👍

@AJenbo AJenbo changed the base branch from master to 9.x December 20, 2022 19:42
@AJenbo
Copy link
Contributor Author

AJenbo commented Dec 20, 2022

@nunomaduro the issues should now have been addressed and the PR has been rebased and targeted towards 9.x

@AJenbo AJenbo marked this pull request as ready for review December 20, 2022 19:46
@nunomaduro nunomaduro marked this pull request as draft December 21, 2022 00:18
@driesvints
Copy link
Member

@AJenbo can you maybe also fix the failing docblock check?

@AJenbo
Copy link
Contributor Author

AJenbo commented Dec 21, 2022

@AJenbo can you maybe also fix the failing docblock check?

@driesvints could you give some input on how it should be resolved?

My thinking is that the tool should allow for additional lines, at least in the bloc preceding the generated part. This would also allow for adding descriptions to Facades.

/**
 * This facade adds a convenient way to interact with the application cache
 * 
 * @template TCacheValue
 *
 * ... generated methods
 */

There also is this line in the tool that I'm not sure if maybe is relevant:
https://github.com/laravel/framework/blob/9.x/bin/facades.php#L213

We could also have it pickup any remaining generics and add them automatically like I have done manually in this PR?

@driesvints
Copy link
Member

Just copy paste the output of the build.

@AJenbo
Copy link
Contributor Author

AJenbo commented Dec 21, 2022

Well I have, and then added the following bit to make it actually valid:

 * @template TCacheValue
 *

@driesvints are you saying that we should go with the non functional generated one for now?

P.s. I think it would also be good to have the tool generate a diff to make the discrepancies more clear. But that is a bit out of scope here.

@driesvints
Copy link
Member

@AJenbo just leave it for now then. We're automating this soon: #45275

@timacdonald
Copy link
Member

I'll fix up the generics Facade docblocks stuff once we merge this one. Don't let it be a blocker.

@nunomaduro
Copy link
Member

Currently working on something else. But I will look at this week at this.

@nunomaduro
Copy link
Member

Made a few adjustments, and added as you as co-author: #45467.

@nunomaduro nunomaduro closed this Dec 30, 2022
@AJenbo AJenbo deleted the generic-cache branch December 30, 2022 16:18
@Tklaversma
Copy link

@nunomaduro Since this update, doing the following will give the error 'void' method 'rememberForever' result used.

    public function doStuff(): string
    {
        return Cache::rememberForever('key', function (): string {
            return 'example';
        });
    }

In other words, it sees the return type TCacheValue on rememberForever() as a void. Probably, because TCacheValue has no declaration.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants