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

[8.x] Auth: Allows to use a callback in credentials array #39420

Merged
merged 2 commits into from
Nov 1, 2021
Merged

[8.x] Auth: Allows to use a callback in credentials array #39420

merged 2 commits into from
Nov 1, 2021

Conversation

DarkGhostHunter
Copy link
Contributor

What?

Allows to use a callback on the Auth::attempt() credentials array:

Auth::attempt([
    'email' => '[email protected]',
    function ($builder) {
        $builder->where('subscription_expires_at', '<', now());
    }
]);

Why?

Both EloquentUserProvider and DatabaseUserProvider only support where() and whereIn() clauses when these receive a credentials array value. This allows to make further adjustments if the value is a callback.

The difference between this and attemptWith() is that this affects the query directly, which is useful to short-circuit the authentication procedure on user retrieval instead of using the aforementioned helper. In some cases, this may help reduce memory consumption as the model/row may not be retrieved before further checks.

BC

None, as is not expected a developer used callbacks in the attempt() array.

Notes

This may be also good for other packages as these can include their own callbacks into the credentials array.

@derekmd
Copy link
Contributor

derekmd commented Oct 30, 2021

String values can be passed into the additional conditions payload so the new conditional may have to be $value instanceof Closure or add ! is_string($value) && is_callable($value) which still allows invokable objects to modify the query. Otherwise this may introduce the same issue as #20692

e.g.,

Auth::attempt([
    'email' => 'foo@bar',
    'password' => 'baz',
    'department' => 'mail',
]);

is_callable('mail') is true because the mail() function exists in the global namespace. mail() is called instead of SQL AND department = 'mail' being appended.

Some other case-insensitive values additional conditions couldn't use include assert, collect, copy, file, e, max, min, link, optional, stat, and view.

@DarkGhostHunter
Copy link
Contributor Author

You're right. Using a value with the same name as a function is a red flag. Try with "mail" => "dd".

It should be strictly a Closure. Totally forgot to force Closures where UGC values may come in as 101.

@taylorotwell taylorotwell merged commit c0b7719 into laravel:8.x Nov 1, 2021
@DarkGhostHunter
Copy link
Contributor Author

DarkGhostHunter commented Nov 1, 2021 via email

@DarkGhostHunter DarkGhostHunter deleted the feat/auth_callback_credential branch November 1, 2021 19:44
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.

3 participants