Upgrade framework
This commit is contained in:
@@ -3,8 +3,112 @@
|
||||
namespace Illuminate\Auth\Access;
|
||||
|
||||
use Exception;
|
||||
use Throwable;
|
||||
|
||||
class AuthorizationException extends Exception
|
||||
{
|
||||
//
|
||||
/**
|
||||
* The response from the gate.
|
||||
*
|
||||
* @var \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
protected $response;
|
||||
|
||||
/**
|
||||
* The HTTP response status code.
|
||||
*
|
||||
* @var int|null
|
||||
*/
|
||||
protected $status;
|
||||
|
||||
/**
|
||||
* Create a new authorization exception instance.
|
||||
*
|
||||
* @param string|null $message
|
||||
* @param mixed $code
|
||||
* @param \Throwable|null $previous
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($message = null, $code = null, Throwable $previous = null)
|
||||
{
|
||||
parent::__construct($message ?? 'This action is unauthorized.', 0, $previous);
|
||||
|
||||
$this->code = $code ?: 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the response from the gate.
|
||||
*
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public function response()
|
||||
{
|
||||
return $this->response;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the response from the gate.
|
||||
*
|
||||
* @param \Illuminate\Auth\Access\Response $response
|
||||
* @return $this
|
||||
*/
|
||||
public function setResponse($response)
|
||||
{
|
||||
$this->response = $response;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the HTTP response status code.
|
||||
*
|
||||
* @param int|null $status
|
||||
* @return $this
|
||||
*/
|
||||
public function withStatus($status)
|
||||
{
|
||||
$this->status = $status;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the HTTP response status code to 404.
|
||||
*
|
||||
* @return $this
|
||||
*/
|
||||
public function asNotFound()
|
||||
{
|
||||
return $this->withStatus(404);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the HTTP status code has been set.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function hasStatus()
|
||||
{
|
||||
return $this->status !== null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the HTTP status code.
|
||||
*
|
||||
* @return int|null
|
||||
*/
|
||||
public function status()
|
||||
{
|
||||
return $this->status;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a deny response object from this exception.
|
||||
*
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public function toResponse()
|
||||
{
|
||||
return Response::deny($this->message, $this->code)->withStatus($this->status);
|
||||
}
|
||||
}
|
||||
|
||||
51
vendor/laravel/framework/src/Illuminate/Auth/Access/Events/GateEvaluated.php
vendored
Normal file
51
vendor/laravel/framework/src/Illuminate/Auth/Access/Events/GateEvaluated.php
vendored
Normal file
@@ -0,0 +1,51 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Access\Events;
|
||||
|
||||
class GateEvaluated
|
||||
{
|
||||
/**
|
||||
* The authenticatable model.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Authenticatable|null
|
||||
*/
|
||||
public $user;
|
||||
|
||||
/**
|
||||
* The ability being evaluated.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $ability;
|
||||
|
||||
/**
|
||||
* The result of the evaluation.
|
||||
*
|
||||
* @var bool|null
|
||||
*/
|
||||
public $result;
|
||||
|
||||
/**
|
||||
* The arguments given during evaluation.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
public $arguments;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param string $ability
|
||||
* @param bool|null $result
|
||||
* @param array $arguments
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($user, $ability, $result, $arguments)
|
||||
{
|
||||
$this->user = $user;
|
||||
$this->ability = $ability;
|
||||
$this->result = $result;
|
||||
$this->arguments = $arguments;
|
||||
}
|
||||
}
|
||||
@@ -2,10 +2,18 @@
|
||||
|
||||
namespace Illuminate\Auth\Access;
|
||||
|
||||
use Closure;
|
||||
use Exception;
|
||||
use Illuminate\Auth\Access\Events\GateEvaluated;
|
||||
use Illuminate\Contracts\Auth\Access\Gate as GateContract;
|
||||
use Illuminate\Contracts\Container\Container;
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
use Illuminate\Support\Arr;
|
||||
use Illuminate\Support\Collection;
|
||||
use Illuminate\Support\Str;
|
||||
use InvalidArgumentException;
|
||||
use Illuminate\Contracts\Container\Container;
|
||||
use Illuminate\Contracts\Auth\Access\Gate as GateContract;
|
||||
use ReflectionClass;
|
||||
use ReflectionFunction;
|
||||
|
||||
class Gate implements GateContract
|
||||
{
|
||||
@@ -53,6 +61,20 @@ class Gate implements GateContract
|
||||
*/
|
||||
protected $afterCallbacks = [];
|
||||
|
||||
/**
|
||||
* All of the defined abilities using class@method notation.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $stringCallbacks = [];
|
||||
|
||||
/**
|
||||
* The callback to be used to guess policy names.
|
||||
*
|
||||
* @var callable|null
|
||||
*/
|
||||
protected $guessPolicyNamesUsingCallback;
|
||||
|
||||
/**
|
||||
* Create a new gate instance.
|
||||
*
|
||||
@@ -62,10 +84,12 @@ class Gate implements GateContract
|
||||
* @param array $policies
|
||||
* @param array $beforeCallbacks
|
||||
* @param array $afterCallbacks
|
||||
* @param callable|null $guessPolicyNamesUsingCallback
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Container $container, callable $userResolver, array $abilities = [],
|
||||
array $policies = [], array $beforeCallbacks = [], array $afterCallbacks = [])
|
||||
array $policies = [], array $beforeCallbacks = [], array $afterCallbacks = [],
|
||||
callable $guessPolicyNamesUsingCallback = null)
|
||||
{
|
||||
$this->policies = $policies;
|
||||
$this->container = $container;
|
||||
@@ -73,36 +97,109 @@ class Gate implements GateContract
|
||||
$this->userResolver = $userResolver;
|
||||
$this->afterCallbacks = $afterCallbacks;
|
||||
$this->beforeCallbacks = $beforeCallbacks;
|
||||
$this->guessPolicyNamesUsingCallback = $guessPolicyNamesUsingCallback;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if a given ability has been defined.
|
||||
*
|
||||
* @param string $ability
|
||||
* @param string|array $ability
|
||||
* @return bool
|
||||
*/
|
||||
public function has($ability)
|
||||
{
|
||||
return isset($this->abilities[$ability]);
|
||||
$abilities = is_array($ability) ? $ability : func_get_args();
|
||||
|
||||
foreach ($abilities as $ability) {
|
||||
if (! isset($this->abilities[$ability])) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform an on-demand authorization check. Throw an authorization exception if the condition or callback is false.
|
||||
*
|
||||
* @param \Illuminate\Auth\Access\Response|\Closure|bool $condition
|
||||
* @param string|null $message
|
||||
* @param string|null $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*
|
||||
* @throws \Illuminate\Auth\Access\AuthorizationException
|
||||
*/
|
||||
public function allowIf($condition, $message = null, $code = null)
|
||||
{
|
||||
return $this->authorizeOnDemand($condition, $message, $code, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform an on-demand authorization check. Throw an authorization exception if the condition or callback is true.
|
||||
*
|
||||
* @param \Illuminate\Auth\Access\Response|\Closure|bool $condition
|
||||
* @param string|null $message
|
||||
* @param string|null $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*
|
||||
* @throws \Illuminate\Auth\Access\AuthorizationException
|
||||
*/
|
||||
public function denyIf($condition, $message = null, $code = null)
|
||||
{
|
||||
return $this->authorizeOnDemand($condition, $message, $code, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Authorize a given condition or callback.
|
||||
*
|
||||
* @param \Illuminate\Auth\Access\Response|\Closure|bool $condition
|
||||
* @param string|null $message
|
||||
* @param string|null $code
|
||||
* @param bool $allowWhenResponseIs
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*
|
||||
* @throws \Illuminate\Auth\Access\AuthorizationException
|
||||
*/
|
||||
protected function authorizeOnDemand($condition, $message, $code, $allowWhenResponseIs)
|
||||
{
|
||||
$user = $this->resolveUser();
|
||||
|
||||
if ($condition instanceof Closure) {
|
||||
$response = $this->canBeCalledWithUser($user, $condition)
|
||||
? $condition($user)
|
||||
: new Response(false, $message, $code);
|
||||
} else {
|
||||
$response = $condition;
|
||||
}
|
||||
|
||||
return with($response instanceof Response ? $response : new Response(
|
||||
(bool) $response === $allowWhenResponseIs, $message, $code
|
||||
))->authorize();
|
||||
}
|
||||
|
||||
/**
|
||||
* Define a new ability.
|
||||
*
|
||||
* @param string $ability
|
||||
* @param callable|string $callback
|
||||
* @param callable|array|string $callback
|
||||
* @return $this
|
||||
*
|
||||
* @throws \InvalidArgumentException
|
||||
*/
|
||||
public function define($ability, $callback)
|
||||
{
|
||||
if (is_array($callback) && isset($callback[0]) && is_string($callback[0])) {
|
||||
$callback = $callback[0].'@'.$callback[1];
|
||||
}
|
||||
|
||||
if (is_callable($callback)) {
|
||||
$this->abilities[$ability] = $callback;
|
||||
} elseif (is_string($callback) && Str::contains($callback, '@')) {
|
||||
$this->abilities[$ability] = $this->buildAbilityCallback($callback);
|
||||
} elseif (is_string($callback)) {
|
||||
$this->stringCallbacks[$ability] = $callback;
|
||||
|
||||
$this->abilities[$ability] = $this->buildAbilityCallback($ability, $callback);
|
||||
} else {
|
||||
throw new InvalidArgumentException("Callback must be a callable or a 'Class@method' string.");
|
||||
throw new InvalidArgumentException("Callback must be a callable, callback array, or a 'Class@method' string.");
|
||||
}
|
||||
|
||||
return $this;
|
||||
@@ -113,13 +210,14 @@ class Gate implements GateContract
|
||||
*
|
||||
* @param string $name
|
||||
* @param string $class
|
||||
* @param array $abilities
|
||||
* @param array|null $abilities
|
||||
* @return $this
|
||||
*/
|
||||
public function resource($name, $class, array $abilities = null)
|
||||
{
|
||||
$abilities = $abilities ?: [
|
||||
'view' => 'view',
|
||||
'viewAny' => 'viewAny',
|
||||
'view' => 'view',
|
||||
'create' => 'create',
|
||||
'update' => 'update',
|
||||
'delete' => 'delete',
|
||||
@@ -135,15 +233,36 @@ class Gate implements GateContract
|
||||
/**
|
||||
* Create the ability callback for a callback string.
|
||||
*
|
||||
* @param string $ability
|
||||
* @param string $callback
|
||||
* @return \Closure
|
||||
*/
|
||||
protected function buildAbilityCallback($callback)
|
||||
protected function buildAbilityCallback($ability, $callback)
|
||||
{
|
||||
return function () use ($callback) {
|
||||
list($class, $method) = Str::parseCallback($callback);
|
||||
return function () use ($ability, $callback) {
|
||||
if (str_contains($callback, '@')) {
|
||||
[$class, $method] = Str::parseCallback($callback);
|
||||
} else {
|
||||
$class = $callback;
|
||||
}
|
||||
|
||||
return $this->resolvePolicy($class)->{$method}(...func_get_args());
|
||||
$policy = $this->resolvePolicy($class);
|
||||
|
||||
$arguments = func_get_args();
|
||||
|
||||
$user = array_shift($arguments);
|
||||
|
||||
$result = $this->callPolicyBefore(
|
||||
$policy, $user, $ability, $arguments
|
||||
);
|
||||
|
||||
if (! is_null($result)) {
|
||||
return $result;
|
||||
}
|
||||
|
||||
return isset($method)
|
||||
? $policy->{$method}(...func_get_args())
|
||||
: $policy(...func_get_args());
|
||||
};
|
||||
}
|
||||
|
||||
@@ -212,19 +331,41 @@ class Gate implements GateContract
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the given ability should be granted for the current user.
|
||||
* Determine if all of the given abilities should be granted for the current user.
|
||||
*
|
||||
* @param string $ability
|
||||
* @param iterable|string $abilities
|
||||
* @param array|mixed $arguments
|
||||
* @return bool
|
||||
*/
|
||||
public function check($ability, $arguments = [])
|
||||
public function check($abilities, $arguments = [])
|
||||
{
|
||||
try {
|
||||
return (bool) $this->raw($ability, $arguments);
|
||||
} catch (AuthorizationException $e) {
|
||||
return false;
|
||||
}
|
||||
return collect($abilities)->every(
|
||||
fn ($ability) => $this->inspect($ability, $arguments)->allowed()
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if any one of the given abilities should be granted for the current user.
|
||||
*
|
||||
* @param iterable|string $abilities
|
||||
* @param array|mixed $arguments
|
||||
* @return bool
|
||||
*/
|
||||
public function any($abilities, $arguments = [])
|
||||
{
|
||||
return collect($abilities)->contains(fn ($ability) => $this->check($ability, $arguments));
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if all of the given abilities should be denied for the current user.
|
||||
*
|
||||
* @param iterable|string $abilities
|
||||
* @param array|mixed $arguments
|
||||
* @return bool
|
||||
*/
|
||||
public function none($abilities, $arguments = [])
|
||||
{
|
||||
return ! $this->any($abilities, $arguments);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -238,13 +379,29 @@ class Gate implements GateContract
|
||||
*/
|
||||
public function authorize($ability, $arguments = [])
|
||||
{
|
||||
$result = $this->raw($ability, $arguments);
|
||||
return $this->inspect($ability, $arguments)->authorize();
|
||||
}
|
||||
|
||||
if ($result instanceof Response) {
|
||||
return $result;
|
||||
/**
|
||||
* Inspect the user for the given ability.
|
||||
*
|
||||
* @param string $ability
|
||||
* @param array|mixed $arguments
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public function inspect($ability, $arguments = [])
|
||||
{
|
||||
try {
|
||||
$result = $this->raw($ability, $arguments);
|
||||
|
||||
if ($result instanceof Response) {
|
||||
return $result;
|
||||
}
|
||||
|
||||
return $result ? Response::allow() : Response::deny();
|
||||
} catch (AuthorizationException $e) {
|
||||
return $e->toResponse();
|
||||
}
|
||||
|
||||
return $result ? $this->allow() : $this->deny();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -253,14 +410,14 @@ class Gate implements GateContract
|
||||
* @param string $ability
|
||||
* @param array|mixed $arguments
|
||||
* @return mixed
|
||||
*
|
||||
* @throws \Illuminate\Auth\Access\AuthorizationException
|
||||
*/
|
||||
protected function raw($ability, $arguments = [])
|
||||
public function raw($ability, $arguments = [])
|
||||
{
|
||||
if (! $user = $this->resolveUser()) {
|
||||
return false;
|
||||
}
|
||||
$arguments = Arr::wrap($arguments);
|
||||
|
||||
$arguments = array_wrap($arguments);
|
||||
$user = $this->resolveUser();
|
||||
|
||||
// First we will call the "before" callbacks for the Gate. If any of these give
|
||||
// back a non-null response, we will immediately return that result in order
|
||||
@@ -276,17 +433,97 @@ class Gate implements GateContract
|
||||
// After calling the authorization callback, we will call the "after" callbacks
|
||||
// that are registered with the Gate, which allows a developer to do logging
|
||||
// if that is required for this application. Then we'll return the result.
|
||||
$this->callAfterCallbacks(
|
||||
return tap($this->callAfterCallbacks(
|
||||
$user, $ability, $arguments, $result
|
||||
);
|
||||
), function ($result) use ($user, $ability, $arguments) {
|
||||
$this->dispatchGateEvaluatedEvent($user, $ability, $arguments, $result);
|
||||
});
|
||||
}
|
||||
|
||||
return $result;
|
||||
/**
|
||||
* Determine whether the callback/method can be called with the given user.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param \Closure|string|array $class
|
||||
* @param string|null $method
|
||||
* @return bool
|
||||
*/
|
||||
protected function canBeCalledWithUser($user, $class, $method = null)
|
||||
{
|
||||
if (! is_null($user)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (! is_null($method)) {
|
||||
return $this->methodAllowsGuests($class, $method);
|
||||
}
|
||||
|
||||
if (is_array($class)) {
|
||||
$className = is_string($class[0]) ? $class[0] : get_class($class[0]);
|
||||
|
||||
return $this->methodAllowsGuests($className, $class[1]);
|
||||
}
|
||||
|
||||
return $this->callbackAllowsGuests($class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the given class method allows guests.
|
||||
*
|
||||
* @param string $class
|
||||
* @param string $method
|
||||
* @return bool
|
||||
*/
|
||||
protected function methodAllowsGuests($class, $method)
|
||||
{
|
||||
try {
|
||||
$reflection = new ReflectionClass($class);
|
||||
|
||||
$method = $reflection->getMethod($method);
|
||||
} catch (Exception $e) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if ($method) {
|
||||
$parameters = $method->getParameters();
|
||||
|
||||
return isset($parameters[0]) && $this->parameterAllowsGuests($parameters[0]);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the callback allows guests.
|
||||
*
|
||||
* @param callable $callback
|
||||
* @return bool
|
||||
*
|
||||
* @throws \ReflectionException
|
||||
*/
|
||||
protected function callbackAllowsGuests($callback)
|
||||
{
|
||||
$parameters = (new ReflectionFunction($callback))->getParameters();
|
||||
|
||||
return isset($parameters[0]) && $this->parameterAllowsGuests($parameters[0]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the given parameter allows guests.
|
||||
*
|
||||
* @param \ReflectionParameter $parameter
|
||||
* @return bool
|
||||
*/
|
||||
protected function parameterAllowsGuests($parameter)
|
||||
{
|
||||
return ($parameter->hasType() && $parameter->allowsNull()) ||
|
||||
($parameter->isDefaultValueAvailable() && is_null($parameter->getDefaultValue()));
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve and call the appropriate authorization callback.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @return bool
|
||||
@@ -301,17 +538,19 @@ class Gate implements GateContract
|
||||
/**
|
||||
* Call all of the before callbacks and return if a result is given.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @return bool|null
|
||||
*/
|
||||
protected function callBeforeCallbacks($user, $ability, array $arguments)
|
||||
{
|
||||
$arguments = array_merge([$user, $ability], [$arguments]);
|
||||
|
||||
foreach ($this->beforeCallbacks as $before) {
|
||||
if (! is_null($result = $before(...$arguments))) {
|
||||
if (! $this->canBeCalledWithUser($user, $before)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (! is_null($result = $before($user, $ability, $arguments))) {
|
||||
return $result;
|
||||
}
|
||||
}
|
||||
@@ -324,39 +563,72 @@ class Gate implements GateContract
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @param bool $result
|
||||
* @return void
|
||||
* @return bool|null
|
||||
*/
|
||||
protected function callAfterCallbacks($user, $ability, array $arguments, $result)
|
||||
{
|
||||
$arguments = array_merge([$user, $ability, $result], [$arguments]);
|
||||
|
||||
foreach ($this->afterCallbacks as $after) {
|
||||
$after(...$arguments);
|
||||
if (! $this->canBeCalledWithUser($user, $after)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$afterResult = $after($user, $ability, $result, $arguments);
|
||||
|
||||
$result ??= $afterResult;
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Dispatch a gate evaluation event.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @param bool|null $result
|
||||
* @return void
|
||||
*/
|
||||
protected function dispatchGateEvaluatedEvent($user, $ability, array $arguments, $result)
|
||||
{
|
||||
if ($this->container->bound(Dispatcher::class)) {
|
||||
$this->container->make(Dispatcher::class)->dispatch(
|
||||
new GateEvaluated($user, $ability, $result, $arguments)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve the callable for the given ability and arguments.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @return callable
|
||||
*/
|
||||
protected function resolveAuthCallback($user, $ability, array $arguments)
|
||||
{
|
||||
if (isset($arguments[0])) {
|
||||
if (! is_null($policy = $this->getPolicyFor($arguments[0]))) {
|
||||
return $this->resolvePolicyCallback($user, $ability, $arguments, $policy);
|
||||
if (isset($arguments[0]) &&
|
||||
! is_null($policy = $this->getPolicyFor($arguments[0])) &&
|
||||
$callback = $this->resolvePolicyCallback($user, $ability, $arguments, $policy)) {
|
||||
return $callback;
|
||||
}
|
||||
|
||||
if (isset($this->stringCallbacks[$ability])) {
|
||||
[$class, $method] = Str::parseCallback($this->stringCallbacks[$ability]);
|
||||
|
||||
if ($this->canBeCalledWithUser($user, $class, $method ?: '__invoke')) {
|
||||
return $this->abilities[$ability];
|
||||
}
|
||||
}
|
||||
|
||||
if (isset($this->abilities[$ability])) {
|
||||
if (isset($this->abilities[$ability]) &&
|
||||
$this->canBeCalledWithUser($user, $this->abilities[$ability])) {
|
||||
return $this->abilities[$ability];
|
||||
}
|
||||
|
||||
return function () {
|
||||
return false;
|
||||
//
|
||||
};
|
||||
}
|
||||
|
||||
@@ -373,13 +645,19 @@ class Gate implements GateContract
|
||||
}
|
||||
|
||||
if (! is_string($class)) {
|
||||
return null;
|
||||
return;
|
||||
}
|
||||
|
||||
if (isset($this->policies[$class])) {
|
||||
return $this->resolvePolicy($this->policies[$class]);
|
||||
}
|
||||
|
||||
foreach ($this->guessPolicyName($class) as $guessedPolicy) {
|
||||
if (class_exists($guessedPolicy)) {
|
||||
return $this->resolvePolicy($guessedPolicy);
|
||||
}
|
||||
}
|
||||
|
||||
foreach ($this->policies as $expected => $policy) {
|
||||
if (is_subclass_of($class, $expected)) {
|
||||
return $this->resolvePolicy($policy);
|
||||
@@ -387,11 +665,51 @@ class Gate implements GateContract
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Guess the policy name for the given class.
|
||||
*
|
||||
* @param string $class
|
||||
* @return array
|
||||
*/
|
||||
protected function guessPolicyName($class)
|
||||
{
|
||||
if ($this->guessPolicyNamesUsingCallback) {
|
||||
return Arr::wrap(call_user_func($this->guessPolicyNamesUsingCallback, $class));
|
||||
}
|
||||
|
||||
$classDirname = str_replace('/', '\\', dirname(str_replace('\\', '/', $class)));
|
||||
|
||||
$classDirnameSegments = explode('\\', $classDirname);
|
||||
|
||||
return Arr::wrap(Collection::times(count($classDirnameSegments), function ($index) use ($class, $classDirnameSegments) {
|
||||
$classDirname = implode('\\', array_slice($classDirnameSegments, 0, $index));
|
||||
|
||||
return $classDirname.'\\Policies\\'.class_basename($class).'Policy';
|
||||
})->reverse()->values()->first(function ($class) {
|
||||
return class_exists($class);
|
||||
}) ?: [$classDirname.'\\Policies\\'.class_basename($class).'Policy']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Specify a callback to be used to guess policy names.
|
||||
*
|
||||
* @param callable $callback
|
||||
* @return $this
|
||||
*/
|
||||
public function guessPolicyNamesUsing(callable $callback)
|
||||
{
|
||||
$this->guessPolicyNamesUsingCallback = $callback;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Build a policy class instance of the given type.
|
||||
*
|
||||
* @param object|string $class
|
||||
* @return mixed
|
||||
*
|
||||
* @throws \Illuminate\Contracts\Container\BindingResolutionException
|
||||
*/
|
||||
public function resolvePolicy($class)
|
||||
{
|
||||
@@ -405,10 +723,14 @@ class Gate implements GateContract
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @param mixed $policy
|
||||
* @return callable
|
||||
* @return bool|callable
|
||||
*/
|
||||
protected function resolvePolicyCallback($user, $ability, array $arguments, $policy)
|
||||
{
|
||||
if (! is_callable([$policy, $this->formatAbilityToMethod($ability)])) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return function () use ($user, $ability, $arguments, $policy) {
|
||||
// This callback will be responsible for calling the policy's before method and
|
||||
// running this policy method if necessary. This is used to when objects are
|
||||
@@ -424,18 +746,9 @@ class Gate implements GateContract
|
||||
return $result;
|
||||
}
|
||||
|
||||
$ability = $this->formatAbilityToMethod($ability);
|
||||
$method = $this->formatAbilityToMethod($ability);
|
||||
|
||||
// If this first argument is a string, that means they are passing a class name
|
||||
// to the policy. We will remove the first argument from this argument array
|
||||
// because this policy already knows what type of models it can authorize.
|
||||
if (isset($arguments[0]) && is_string($arguments[0])) {
|
||||
array_shift($arguments);
|
||||
}
|
||||
|
||||
return is_callable([$policy, $ability])
|
||||
? $policy->{$ability}($user, ...$arguments)
|
||||
: false;
|
||||
return $this->callPolicyMethod($policy, $method, $user, $arguments);
|
||||
};
|
||||
}
|
||||
|
||||
@@ -450,11 +763,42 @@ class Gate implements GateContract
|
||||
*/
|
||||
protected function callPolicyBefore($policy, $user, $ability, $arguments)
|
||||
{
|
||||
if (method_exists($policy, 'before')) {
|
||||
if (! method_exists($policy, 'before')) {
|
||||
return;
|
||||
}
|
||||
|
||||
if ($this->canBeCalledWithUser($user, $policy, 'before')) {
|
||||
return $policy->before($user, $ability, ...$arguments);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Call the appropriate method on the given policy.
|
||||
*
|
||||
* @param mixed $policy
|
||||
* @param string $method
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param array $arguments
|
||||
* @return mixed
|
||||
*/
|
||||
protected function callPolicyMethod($policy, $method, $user, array $arguments)
|
||||
{
|
||||
// If this first argument is a string, that means they are passing a class name
|
||||
// to the policy. We will remove the first argument from this argument array
|
||||
// because this policy already knows what type of models it can authorize.
|
||||
if (isset($arguments[0]) && is_string($arguments[0])) {
|
||||
array_shift($arguments);
|
||||
}
|
||||
|
||||
if (! is_callable([$policy, $method])) {
|
||||
return;
|
||||
}
|
||||
|
||||
if ($this->canBeCalledWithUser($user, $policy, $method)) {
|
||||
return $policy->{$method}($user, ...$arguments);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Format the policy ability into a method name.
|
||||
*
|
||||
@@ -463,7 +807,7 @@ class Gate implements GateContract
|
||||
*/
|
||||
protected function formatAbilityToMethod($ability)
|
||||
{
|
||||
return strpos($ability, '-') !== false ? Str::camel($ability) : $ability;
|
||||
return str_contains($ability, '-') ? Str::camel($ability) : $ability;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -474,13 +818,12 @@ class Gate implements GateContract
|
||||
*/
|
||||
public function forUser($user)
|
||||
{
|
||||
$callback = function () use ($user) {
|
||||
return $user;
|
||||
};
|
||||
$callback = fn () => $user;
|
||||
|
||||
return new static(
|
||||
$this->container, $callback, $this->abilities,
|
||||
$this->policies, $this->beforeCallbacks, $this->afterCallbacks
|
||||
$this->policies, $this->beforeCallbacks, $this->afterCallbacks,
|
||||
$this->guessPolicyNamesUsingCallback
|
||||
);
|
||||
}
|
||||
|
||||
@@ -503,4 +846,27 @@ class Gate implements GateContract
|
||||
{
|
||||
return $this->abilities;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all of the defined policies.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
public function policies()
|
||||
{
|
||||
return $this->policies;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the container instance used by the gate.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Container\Container $container
|
||||
* @return $this
|
||||
*/
|
||||
public function setContainer(Container $container)
|
||||
{
|
||||
$this->container = $container;
|
||||
|
||||
return $this;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,23 +8,48 @@ trait HandlesAuthorization
|
||||
* Create a new access response.
|
||||
*
|
||||
* @param string|null $message
|
||||
* @param mixed $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
protected function allow($message = null)
|
||||
protected function allow($message = null, $code = null)
|
||||
{
|
||||
return new Response($message);
|
||||
return Response::allow($message, $code);
|
||||
}
|
||||
|
||||
/**
|
||||
* Throws an unauthorized exception.
|
||||
*
|
||||
* @param string $message
|
||||
* @return void
|
||||
*
|
||||
* @throws \Illuminate\Auth\Access\AuthorizationException
|
||||
* @param string|null $message
|
||||
* @param mixed|null $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
protected function deny($message = 'This action is unauthorized.')
|
||||
protected function deny($message = null, $code = null)
|
||||
{
|
||||
throw new AuthorizationException($message);
|
||||
return Response::deny($message, $code);
|
||||
}
|
||||
|
||||
/**
|
||||
* Deny with a HTTP status code.
|
||||
*
|
||||
* @param int $status
|
||||
* @param ?string $message
|
||||
* @param ?int $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public function denyWithStatus($status, $message = null, $code = null)
|
||||
{
|
||||
return Response::denyWithStatus($status, $message, $code);
|
||||
}
|
||||
|
||||
/**
|
||||
* Deny with a 404 HTTP status code.
|
||||
*
|
||||
* @param ?string $message
|
||||
* @param ?int $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public function denyAsNotFound($message = null, $code = null)
|
||||
{
|
||||
return Response::denyWithStatus(404, $message, $code);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,8 +2,17 @@
|
||||
|
||||
namespace Illuminate\Auth\Access;
|
||||
|
||||
class Response
|
||||
use Illuminate\Contracts\Support\Arrayable;
|
||||
|
||||
class Response implements Arrayable
|
||||
{
|
||||
/**
|
||||
* Indicates whether the response was allowed.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
protected $allowed;
|
||||
|
||||
/**
|
||||
* The response message.
|
||||
*
|
||||
@@ -11,16 +20,104 @@ class Response
|
||||
*/
|
||||
protected $message;
|
||||
|
||||
/**
|
||||
* The response code.
|
||||
*
|
||||
* @var mixed
|
||||
*/
|
||||
protected $code;
|
||||
|
||||
/**
|
||||
* The HTTP response status code.
|
||||
*
|
||||
* @var int|null
|
||||
*/
|
||||
protected $status;
|
||||
|
||||
/**
|
||||
* Create a new response.
|
||||
*
|
||||
* @param string|null $message
|
||||
* @param bool $allowed
|
||||
* @param string $message
|
||||
* @param mixed $code
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($message = null)
|
||||
public function __construct($allowed, $message = '', $code = null)
|
||||
{
|
||||
$this->code = $code;
|
||||
$this->allowed = $allowed;
|
||||
$this->message = $message;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new "allow" Response.
|
||||
*
|
||||
* @param string|null $message
|
||||
* @param mixed $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public static function allow($message = null, $code = null)
|
||||
{
|
||||
return new static(true, $message, $code);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new "deny" Response.
|
||||
*
|
||||
* @param string|null $message
|
||||
* @param mixed $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public static function deny($message = null, $code = null)
|
||||
{
|
||||
return new static(false, $message, $code);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new "deny" Response with a HTTP status code.
|
||||
*
|
||||
* @param int $status
|
||||
* @param string|null $message
|
||||
* @param mixed $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public static function denyWithStatus($status, $message = null, $code = null)
|
||||
{
|
||||
return static::deny($message, $code)->withStatus($status);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new "deny" Response with a 404 HTTP status code.
|
||||
*
|
||||
* @param string|null $message
|
||||
* @param mixed $code
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*/
|
||||
public static function denyAsNotFound($message = null, $code = null)
|
||||
{
|
||||
return static::denyWithStatus(404, $message, $code);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the response was allowed.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function allowed()
|
||||
{
|
||||
return $this->allowed;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the response was denied.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function denied()
|
||||
{
|
||||
return ! $this->allowed();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the response message.
|
||||
*
|
||||
@@ -31,6 +128,81 @@ class Response
|
||||
return $this->message;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the response code / reason.
|
||||
*
|
||||
* @return mixed
|
||||
*/
|
||||
public function code()
|
||||
{
|
||||
return $this->code;
|
||||
}
|
||||
|
||||
/**
|
||||
* Throw authorization exception if response was denied.
|
||||
*
|
||||
* @return \Illuminate\Auth\Access\Response
|
||||
*
|
||||
* @throws \Illuminate\Auth\Access\AuthorizationException
|
||||
*/
|
||||
public function authorize()
|
||||
{
|
||||
if ($this->denied()) {
|
||||
throw (new AuthorizationException($this->message(), $this->code()))
|
||||
->setResponse($this)
|
||||
->withStatus($this->status);
|
||||
}
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the HTTP response status code.
|
||||
*
|
||||
* @param null|int $status
|
||||
* @return $this
|
||||
*/
|
||||
public function withStatus($status)
|
||||
{
|
||||
$this->status = $status;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the HTTP response status code to 404.
|
||||
*
|
||||
* @return $this
|
||||
*/
|
||||
public function asNotFound()
|
||||
{
|
||||
return $this->withStatus(404);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the HTTP status code.
|
||||
*
|
||||
* @return int|null
|
||||
*/
|
||||
public function status()
|
||||
{
|
||||
return $this->status;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert the response to an array.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
public function toArray()
|
||||
{
|
||||
return [
|
||||
'allowed' => $this->allowed(),
|
||||
'message' => $this->message(),
|
||||
'code' => $this->code(),
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the string representation of the message.
|
||||
*
|
||||
@@ -38,6 +210,6 @@ class Response
|
||||
*/
|
||||
public function __toString()
|
||||
{
|
||||
return $this->message();
|
||||
return (string) $this->message();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,9 +3,13 @@
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Closure;
|
||||
use InvalidArgumentException;
|
||||
use Illuminate\Contracts\Auth\Factory as FactoryContract;
|
||||
use InvalidArgumentException;
|
||||
|
||||
/**
|
||||
* @mixin \Illuminate\Contracts\Auth\Guard
|
||||
* @mixin \Illuminate\Contracts\Auth\StatefulGuard
|
||||
*/
|
||||
class AuthManager implements FactoryContract
|
||||
{
|
||||
use CreatesUserProviders;
|
||||
@@ -13,7 +17,7 @@ class AuthManager implements FactoryContract
|
||||
/**
|
||||
* The application instance.
|
||||
*
|
||||
* @var \Illuminate\Foundation\Application
|
||||
* @var \Illuminate\Contracts\Foundation\Application
|
||||
*/
|
||||
protected $app;
|
||||
|
||||
@@ -43,31 +47,27 @@ class AuthManager implements FactoryContract
|
||||
/**
|
||||
* Create a new Auth manager instance.
|
||||
*
|
||||
* @param \Illuminate\Foundation\Application $app
|
||||
* @param \Illuminate\Contracts\Foundation\Application $app
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($app)
|
||||
{
|
||||
$this->app = $app;
|
||||
|
||||
$this->userResolver = function ($guard = null) {
|
||||
return $this->guard($guard)->user();
|
||||
};
|
||||
$this->userResolver = fn ($guard = null) => $this->guard($guard)->user();
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to get the guard from the local cache.
|
||||
*
|
||||
* @param string $name
|
||||
* @param string|null $name
|
||||
* @return \Illuminate\Contracts\Auth\Guard|\Illuminate\Contracts\Auth\StatefulGuard
|
||||
*/
|
||||
public function guard($name = null)
|
||||
{
|
||||
$name = $name ?: $this->getDefaultDriver();
|
||||
|
||||
return isset($this->guards[$name])
|
||||
? $this->guards[$name]
|
||||
: $this->guards[$name] = $this->resolve($name);
|
||||
return $this->guards[$name] ?? $this->guards[$name] = $this->resolve($name);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -96,7 +96,9 @@ class AuthManager implements FactoryContract
|
||||
return $this->{$driverMethod}($name, $config);
|
||||
}
|
||||
|
||||
throw new InvalidArgumentException("Auth guard driver [{$name}] is not defined.");
|
||||
throw new InvalidArgumentException(
|
||||
"Auth driver [{$config['driver']}] for guard [{$name}] is not defined."
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -120,9 +122,13 @@ class AuthManager implements FactoryContract
|
||||
*/
|
||||
public function createSessionDriver($name, $config)
|
||||
{
|
||||
$provider = $this->createUserProvider($config['provider']);
|
||||
$provider = $this->createUserProvider($config['provider'] ?? null);
|
||||
|
||||
$guard = new SessionGuard($name, $provider, $this->app['session.store']);
|
||||
$guard = new SessionGuard(
|
||||
$name,
|
||||
$provider,
|
||||
$this->app['session.store'],
|
||||
);
|
||||
|
||||
// When using the remember me functionality of the authentication services we
|
||||
// will need to be set the encryption instance of the guard, which allows
|
||||
@@ -139,6 +145,10 @@ class AuthManager implements FactoryContract
|
||||
$guard->setRequest($this->app->refresh('request', $guard, 'setRequest'));
|
||||
}
|
||||
|
||||
if (isset($config['remember'])) {
|
||||
$guard->setRememberDuration($config['remember']);
|
||||
}
|
||||
|
||||
return $guard;
|
||||
}
|
||||
|
||||
@@ -155,8 +165,11 @@ class AuthManager implements FactoryContract
|
||||
// that takes an API token field from the request and matches it to the
|
||||
// user in the database or another persistence layer where users are.
|
||||
$guard = new TokenGuard(
|
||||
$this->createUserProvider($config['provider']),
|
||||
$this->app['request']
|
||||
$this->createUserProvider($config['provider'] ?? null),
|
||||
$this->app['request'],
|
||||
$config['input_key'] ?? 'api_token',
|
||||
$config['storage_key'] ?? 'api_token',
|
||||
$config['hash'] ?? false
|
||||
);
|
||||
|
||||
$this->app->refresh('request', $guard, 'setRequest');
|
||||
@@ -197,9 +210,7 @@ class AuthManager implements FactoryContract
|
||||
|
||||
$this->setDefaultDriver($name);
|
||||
|
||||
$this->userResolver = function ($name = null) {
|
||||
return $this->guard($name)->user();
|
||||
};
|
||||
$this->userResolver = fn ($name = null) => $this->guard($name)->user();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -223,7 +234,7 @@ class AuthManager implements FactoryContract
|
||||
public function viaRequest($driver, callable $callback)
|
||||
{
|
||||
return $this->extend($driver, function () use ($callback) {
|
||||
$guard = new RequestGuard($callback, $this->app['request']);
|
||||
$guard = new RequestGuard($callback, $this->app['request'], $this->createUserProvider());
|
||||
|
||||
$this->app->refresh('request', $guard, 'setRequest');
|
||||
|
||||
@@ -282,6 +293,41 @@ class AuthManager implements FactoryContract
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determines if any guards have already been resolved.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function hasResolvedGuards()
|
||||
{
|
||||
return count($this->guards) > 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Forget all of the resolved guard instances.
|
||||
*
|
||||
* @return $this
|
||||
*/
|
||||
public function forgetGuards()
|
||||
{
|
||||
$this->guards = [];
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the application instance used by the manager.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Foundation\Application $app
|
||||
* @return $this
|
||||
*/
|
||||
public function setApplication($app)
|
||||
{
|
||||
$this->app = $app;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Dynamically call the default driver instance.
|
||||
*
|
||||
|
||||
@@ -3,9 +3,12 @@
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Auth\Access\Gate;
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Auth\Middleware\RequirePassword;
|
||||
use Illuminate\Contracts\Auth\Access\Gate as GateContract;
|
||||
use Illuminate\Contracts\Auth\Authenticatable as AuthenticatableContract;
|
||||
use Illuminate\Contracts\Routing\ResponseFactory;
|
||||
use Illuminate\Contracts\Routing\UrlGenerator;
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
|
||||
class AuthServiceProvider extends ServiceProvider
|
||||
{
|
||||
@@ -17,12 +20,11 @@ class AuthServiceProvider extends ServiceProvider
|
||||
public function register()
|
||||
{
|
||||
$this->registerAuthenticator();
|
||||
|
||||
$this->registerUserResolver();
|
||||
|
||||
$this->registerAccessGate();
|
||||
|
||||
$this->registerRequirePassword();
|
||||
$this->registerRequestRebindHandler();
|
||||
$this->registerEventRebindHandler();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -32,18 +34,9 @@ class AuthServiceProvider extends ServiceProvider
|
||||
*/
|
||||
protected function registerAuthenticator()
|
||||
{
|
||||
$this->app->singleton('auth', function ($app) {
|
||||
// Once the authentication service has actually been requested by the developer
|
||||
// we will set a variable in the application indicating such. This helps us
|
||||
// know that we need to set any queued cookies in the after event later.
|
||||
$app['auth.loaded'] = true;
|
||||
$this->app->singleton('auth', fn ($app) => new AuthManager($app));
|
||||
|
||||
return new AuthManager($app);
|
||||
});
|
||||
|
||||
$this->app->singleton('auth.driver', function ($app) {
|
||||
return $app['auth']->guard();
|
||||
});
|
||||
$this->app->singleton('auth.driver', fn ($app) => $app['auth']->guard());
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -53,11 +46,7 @@ class AuthServiceProvider extends ServiceProvider
|
||||
*/
|
||||
protected function registerUserResolver()
|
||||
{
|
||||
$this->app->bind(
|
||||
AuthenticatableContract::class, function ($app) {
|
||||
return call_user_func($app['auth']->userResolver());
|
||||
}
|
||||
);
|
||||
$this->app->bind(AuthenticatableContract::class, fn ($app) => call_user_func($app['auth']->userResolver()));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -68,9 +57,7 @@ class AuthServiceProvider extends ServiceProvider
|
||||
protected function registerAccessGate()
|
||||
{
|
||||
$this->app->singleton(GateContract::class, function ($app) {
|
||||
return new Gate($app, function () use ($app) {
|
||||
return call_user_func($app['auth']->userResolver());
|
||||
});
|
||||
return new Gate($app, fn () => call_user_func($app['auth']->userResolver()));
|
||||
});
|
||||
}
|
||||
|
||||
@@ -79,6 +66,22 @@ class AuthServiceProvider extends ServiceProvider
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function registerRequirePassword()
|
||||
{
|
||||
$this->app->bind(RequirePassword::class, function ($app) {
|
||||
return new RequirePassword(
|
||||
$app[ResponseFactory::class],
|
||||
$app[UrlGenerator::class],
|
||||
$app['config']->get('auth.password_timeout')
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle the re-binding of the request binding.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function registerRequestRebindHandler()
|
||||
{
|
||||
$this->app->rebinding('request', function ($app, $request) {
|
||||
@@ -87,4 +90,23 @@ class AuthServiceProvider extends ServiceProvider
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle the re-binding of the event dispatcher binding.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function registerEventRebindHandler()
|
||||
{
|
||||
$this->app->rebinding('events', function ($app, $dispatcher) {
|
||||
if (! $app->resolved('auth') ||
|
||||
$app['auth']->hasResolvedGuards() === false) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (method_exists($guard = $app['auth']->guard(), 'setDispatcher')) {
|
||||
$guard->setDispatcher($dispatcher);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -31,6 +31,16 @@ trait Authenticatable
|
||||
return $this->{$this->getAuthIdentifierName()};
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the unique broadcast identifier for the user.
|
||||
*
|
||||
* @return mixed
|
||||
*/
|
||||
public function getAuthIdentifierForBroadcasting()
|
||||
{
|
||||
return $this->getAuthIdentifier();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the password for the user.
|
||||
*
|
||||
@@ -44,12 +54,12 @@ trait Authenticatable
|
||||
/**
|
||||
* Get the token value for the "remember me" session.
|
||||
*
|
||||
* @return string
|
||||
* @return string|null
|
||||
*/
|
||||
public function getRememberToken()
|
||||
{
|
||||
if (! empty($this->getRememberTokenName())) {
|
||||
return $this->{$this->getRememberTokenName()};
|
||||
return (string) $this->{$this->getRememberTokenName()};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -13,18 +13,27 @@ class AuthenticationException extends Exception
|
||||
*/
|
||||
protected $guards;
|
||||
|
||||
/**
|
||||
* The path the user should be redirected to.
|
||||
*
|
||||
* @var string|null
|
||||
*/
|
||||
protected $redirectTo;
|
||||
|
||||
/**
|
||||
* Create a new authentication exception.
|
||||
*
|
||||
* @param string $message
|
||||
* @param array $guards
|
||||
* @param string|null $redirectTo
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($message = 'Unauthenticated.', array $guards = [])
|
||||
public function __construct($message = 'Unauthenticated.', array $guards = [], $redirectTo = null)
|
||||
{
|
||||
parent::__construct($message);
|
||||
|
||||
$this->guards = $guards;
|
||||
$this->redirectTo = $redirectTo;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -36,4 +45,14 @@ class AuthenticationException extends Exception
|
||||
{
|
||||
return $this->guards;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the path the user should be redirected to.
|
||||
*
|
||||
* @return string|null
|
||||
*/
|
||||
public function redirectTo()
|
||||
{
|
||||
return $this->redirectTo;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,7 +3,9 @@
|
||||
namespace Illuminate\Auth\Console;
|
||||
|
||||
use Illuminate\Console\Command;
|
||||
use Symfony\Component\Console\Attribute\AsCommand;
|
||||
|
||||
#[AsCommand(name: 'auth:clear-resets')]
|
||||
class ClearResetsCommand extends Command
|
||||
{
|
||||
/**
|
||||
@@ -13,6 +15,17 @@ class ClearResetsCommand extends Command
|
||||
*/
|
||||
protected $signature = 'auth:clear-resets {name? : The name of the password broker}';
|
||||
|
||||
/**
|
||||
* The name of the console command.
|
||||
*
|
||||
* This name is used to identify the command during lazy loading.
|
||||
*
|
||||
* @var string|null
|
||||
*
|
||||
* @deprecated
|
||||
*/
|
||||
protected static $defaultName = 'auth:clear-resets';
|
||||
|
||||
/**
|
||||
* The console command description.
|
||||
*
|
||||
@@ -25,10 +38,10 @@ class ClearResetsCommand extends Command
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function fire()
|
||||
public function handle()
|
||||
{
|
||||
$this->laravel['auth.password']->broker($this->argument('name'))->getRepository()->deleteExpired();
|
||||
|
||||
$this->info('Expired reset tokens cleared!');
|
||||
$this->components->info('Expired reset tokens cleared successfully.');
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,119 +0,0 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Console;
|
||||
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Console\DetectsApplicationNamespace;
|
||||
|
||||
class MakeAuthCommand extends Command
|
||||
{
|
||||
use DetectsApplicationNamespace;
|
||||
|
||||
/**
|
||||
* The name and signature of the console command.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $signature = 'make:auth
|
||||
{--views : Only scaffold the authentication views}
|
||||
{--force : Overwrite existing views by default}';
|
||||
|
||||
/**
|
||||
* The console command description.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $description = 'Scaffold basic login and registration views and routes';
|
||||
|
||||
/**
|
||||
* The views that need to be exported.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $views = [
|
||||
'auth/login.stub' => 'auth/login.blade.php',
|
||||
'auth/register.stub' => 'auth/register.blade.php',
|
||||
'auth/passwords/email.stub' => 'auth/passwords/email.blade.php',
|
||||
'auth/passwords/reset.stub' => 'auth/passwords/reset.blade.php',
|
||||
'layouts/app.stub' => 'layouts/app.blade.php',
|
||||
'home.stub' => 'home.blade.php',
|
||||
];
|
||||
|
||||
/**
|
||||
* Execute the console command.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function fire()
|
||||
{
|
||||
$this->createDirectories();
|
||||
|
||||
$this->exportViews();
|
||||
|
||||
if (! $this->option('views')) {
|
||||
file_put_contents(
|
||||
app_path('Http/Controllers/HomeController.php'),
|
||||
$this->compileControllerStub()
|
||||
);
|
||||
|
||||
file_put_contents(
|
||||
base_path('routes/web.php'),
|
||||
file_get_contents(__DIR__.'/stubs/make/routes.stub'),
|
||||
FILE_APPEND
|
||||
);
|
||||
}
|
||||
|
||||
$this->info('Authentication scaffolding generated successfully.');
|
||||
}
|
||||
|
||||
/**
|
||||
* Create the directories for the files.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function createDirectories()
|
||||
{
|
||||
if (! is_dir(resource_path('views/layouts'))) {
|
||||
mkdir(resource_path('views/layouts'), 0755, true);
|
||||
}
|
||||
|
||||
if (! is_dir(resource_path('views/auth/passwords'))) {
|
||||
mkdir(resource_path('views/auth/passwords'), 0755, true);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Export the authentication views.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function exportViews()
|
||||
{
|
||||
foreach ($this->views as $key => $value) {
|
||||
if (file_exists(resource_path('views/'.$value)) && ! $this->option('force')) {
|
||||
if (! $this->confirm("The [{$value}] view already exists. Do you want to replace it?")) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
copy(
|
||||
__DIR__.'/stubs/make/views/'.$key,
|
||||
resource_path('views/'.$value)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Compiles the HomeController stub.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
protected function compileControllerStub()
|
||||
{
|
||||
return str_replace(
|
||||
'{{namespace}}',
|
||||
$this->getAppNamespace(),
|
||||
file_get_contents(__DIR__.'/stubs/make/controllers/HomeController.stub')
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
<?php
|
||||
|
||||
namespace {{namespace}}Http\Controllers;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class HomeController extends Controller
|
||||
{
|
||||
/**
|
||||
* Create a new controller instance.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->middleware('auth');
|
||||
}
|
||||
|
||||
/**
|
||||
* Show the application dashboard.
|
||||
*
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function index()
|
||||
{
|
||||
return view('home');
|
||||
}
|
||||
}
|
||||
@@ -1,4 +0,0 @@
|
||||
|
||||
Auth::routes();
|
||||
|
||||
Route::get('/home', 'HomeController@index')->name('home');
|
||||
@@ -1,68 +0,0 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('content')
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-8 col-md-offset-2">
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading">Login</div>
|
||||
<div class="panel-body">
|
||||
<form class="form-horizontal" method="POST" action="{{ route('login') }}">
|
||||
{{ csrf_field() }}
|
||||
|
||||
<div class="form-group{{ $errors->has('email') ? ' has-error' : '' }}">
|
||||
<label for="email" class="col-md-4 control-label">E-Mail Address</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="email" type="email" class="form-control" name="email" value="{{ old('email') }}" required autofocus>
|
||||
|
||||
@if ($errors->has('email'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('email') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group{{ $errors->has('password') ? ' has-error' : '' }}">
|
||||
<label for="password" class="col-md-4 control-label">Password</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="password" type="password" class="form-control" name="password" required>
|
||||
|
||||
@if ($errors->has('password'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('password') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<div class="col-md-6 col-md-offset-4">
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" name="remember" {{ old('remember') ? 'checked' : '' }}> Remember Me
|
||||
</label>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<div class="col-md-8 col-md-offset-4">
|
||||
<button type="submit" class="btn btn-primary">
|
||||
Login
|
||||
</button>
|
||||
|
||||
<a class="btn btn-link" href="{{ route('password.request') }}">
|
||||
Forgot Your Password?
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
@@ -1,46 +0,0 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('content')
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-8 col-md-offset-2">
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading">Reset Password</div>
|
||||
<div class="panel-body">
|
||||
@if (session('status'))
|
||||
<div class="alert alert-success">
|
||||
{{ session('status') }}
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<form class="form-horizontal" method="POST" action="{{ route('password.email') }}">
|
||||
{{ csrf_field() }}
|
||||
|
||||
<div class="form-group{{ $errors->has('email') ? ' has-error' : '' }}">
|
||||
<label for="email" class="col-md-4 control-label">E-Mail Address</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="email" type="email" class="form-control" name="email" value="{{ old('email') }}" required>
|
||||
|
||||
@if ($errors->has('email'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('email') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<div class="col-md-6 col-md-offset-4">
|
||||
<button type="submit" class="btn btn-primary">
|
||||
Send Password Reset Link
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
@@ -1,76 +0,0 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('content')
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-8 col-md-offset-2">
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading">Reset Password</div>
|
||||
|
||||
<div class="panel-body">
|
||||
@if (session('status'))
|
||||
<div class="alert alert-success">
|
||||
{{ session('status') }}
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<form class="form-horizontal" method="POST" action="{{ route('password.request') }}">
|
||||
{{ csrf_field() }}
|
||||
|
||||
<input type="hidden" name="token" value="{{ $token }}">
|
||||
|
||||
<div class="form-group{{ $errors->has('email') ? ' has-error' : '' }}">
|
||||
<label for="email" class="col-md-4 control-label">E-Mail Address</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="email" type="email" class="form-control" name="email" value="{{ $email or old('email') }}" required autofocus>
|
||||
|
||||
@if ($errors->has('email'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('email') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group{{ $errors->has('password') ? ' has-error' : '' }}">
|
||||
<label for="password" class="col-md-4 control-label">Password</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="password" type="password" class="form-control" name="password" required>
|
||||
|
||||
@if ($errors->has('password'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('password') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group{{ $errors->has('password_confirmation') ? ' has-error' : '' }}">
|
||||
<label for="password-confirm" class="col-md-4 control-label">Confirm Password</label>
|
||||
<div class="col-md-6">
|
||||
<input id="password-confirm" type="password" class="form-control" name="password_confirmation" required>
|
||||
|
||||
@if ($errors->has('password_confirmation'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('password_confirmation') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<div class="col-md-6 col-md-offset-4">
|
||||
<button type="submit" class="btn btn-primary">
|
||||
Reset Password
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
@@ -1,76 +0,0 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('content')
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-8 col-md-offset-2">
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading">Register</div>
|
||||
<div class="panel-body">
|
||||
<form class="form-horizontal" method="POST" action="{{ route('register') }}">
|
||||
{{ csrf_field() }}
|
||||
|
||||
<div class="form-group{{ $errors->has('name') ? ' has-error' : '' }}">
|
||||
<label for="name" class="col-md-4 control-label">Name</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="name" type="text" class="form-control" name="name" value="{{ old('name') }}" required autofocus>
|
||||
|
||||
@if ($errors->has('name'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('name') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group{{ $errors->has('email') ? ' has-error' : '' }}">
|
||||
<label for="email" class="col-md-4 control-label">E-Mail Address</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="email" type="email" class="form-control" name="email" value="{{ old('email') }}" required>
|
||||
|
||||
@if ($errors->has('email'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('email') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group{{ $errors->has('password') ? ' has-error' : '' }}">
|
||||
<label for="password" class="col-md-4 control-label">Password</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="password" type="password" class="form-control" name="password" required>
|
||||
|
||||
@if ($errors->has('password'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('password') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<label for="password-confirm" class="col-md-4 control-label">Confirm Password</label>
|
||||
|
||||
<div class="col-md-6">
|
||||
<input id="password-confirm" type="password" class="form-control" name="password_confirmation" required>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<div class="col-md-6 col-md-offset-4">
|
||||
<button type="submit" class="btn btn-primary">
|
||||
Register
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
@@ -1,17 +0,0 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('content')
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-8 col-md-offset-2">
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading">Dashboard</div>
|
||||
|
||||
<div class="panel-body">
|
||||
You are logged in!
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
||||
@@ -1,8 +1,7 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="{{ app()->getLocale() }}">
|
||||
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
|
||||
<!-- CSRF Token -->
|
||||
@@ -10,71 +9,68 @@
|
||||
|
||||
<title>{{ config('app.name', 'Laravel') }}</title>
|
||||
|
||||
<!-- Scripts -->
|
||||
<script src="{{ asset('js/app.js') }}" defer></script>
|
||||
|
||||
<!-- Styles -->
|
||||
<link href="{{ asset('css/app.css') }}" rel="stylesheet">
|
||||
</head>
|
||||
<body>
|
||||
<div id="app">
|
||||
<nav class="navbar navbar-default navbar-static-top">
|
||||
<nav class="navbar navbar-expand-md navbar-light bg-white shadow-sm">
|
||||
<div class="container">
|
||||
<div class="navbar-header">
|
||||
<a class="navbar-brand" href="{{ url('/') }}">
|
||||
{{ config('app.name', 'Laravel') }}
|
||||
</a>
|
||||
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="{{ __('Toggle navigation') }}">
|
||||
<span class="navbar-toggler-icon"></span>
|
||||
</button>
|
||||
|
||||
<!-- Collapsed Hamburger -->
|
||||
<button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#app-navbar-collapse">
|
||||
<span class="sr-only">Toggle Navigation</span>
|
||||
<span class="icon-bar"></span>
|
||||
<span class="icon-bar"></span>
|
||||
<span class="icon-bar"></span>
|
||||
</button>
|
||||
|
||||
<!-- Branding Image -->
|
||||
<a class="navbar-brand" href="{{ url('/') }}">
|
||||
{{ config('app.name', 'Laravel') }}
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div class="collapse navbar-collapse" id="app-navbar-collapse">
|
||||
<div class="collapse navbar-collapse" id="navbarSupportedContent">
|
||||
<!-- Left Side Of Navbar -->
|
||||
<ul class="nav navbar-nav">
|
||||
|
||||
<ul class="navbar-nav mr-auto">
|
||||
|
||||
</ul>
|
||||
|
||||
<!-- Right Side Of Navbar -->
|
||||
<ul class="nav navbar-nav navbar-right">
|
||||
<ul class="navbar-nav ml-auto">
|
||||
<!-- Authentication Links -->
|
||||
@if (Auth::guest())
|
||||
<li><a href="{{ route('login') }}">Login</a></li>
|
||||
<li><a href="{{ route('register') }}">Register</a></li>
|
||||
@guest
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="{{ route('login') }}">{{ __('Login') }}</a>
|
||||
</li>
|
||||
@if (Route::has('register'))
|
||||
<li class="nav-item">
|
||||
<a class="nav-link" href="{{ route('register') }}">{{ __('Register') }}</a>
|
||||
</li>
|
||||
@endif
|
||||
@else
|
||||
<li class="dropdown">
|
||||
<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">
|
||||
<li class="nav-item dropdown">
|
||||
<a id="navbarDropdown" class="nav-link dropdown-toggle" href="#" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" v-pre>
|
||||
{{ Auth::user()->name }} <span class="caret"></span>
|
||||
</a>
|
||||
|
||||
<ul class="dropdown-menu" role="menu">
|
||||
<li>
|
||||
<a href="{{ route('logout') }}"
|
||||
onclick="event.preventDefault();
|
||||
<div class="dropdown-menu dropdown-menu-right" aria-labelledby="navbarDropdown">
|
||||
<a class="dropdown-item" href="{{ route('logout') }}"
|
||||
onclick="event.preventDefault();
|
||||
document.getElementById('logout-form').submit();">
|
||||
Logout
|
||||
</a>
|
||||
{{ __('Logout') }}
|
||||
</a>
|
||||
|
||||
<form id="logout-form" action="{{ route('logout') }}" method="POST" style="display: none;">
|
||||
{{ csrf_field() }}
|
||||
</form>
|
||||
</li>
|
||||
</ul>
|
||||
<form id="logout-form" action="{{ route('logout') }}" method="POST" style="display: none;">
|
||||
@csrf
|
||||
</form>
|
||||
</div>
|
||||
</li>
|
||||
@endif
|
||||
@endguest
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
@yield('content')
|
||||
<main class="py-4">
|
||||
@yield('content')
|
||||
</main>
|
||||
</div>
|
||||
|
||||
<!-- Scripts -->
|
||||
<script src="{{ asset('js/app.js') }}"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
||||
@@ -16,28 +16,42 @@ trait CreatesUserProviders
|
||||
/**
|
||||
* Create the user provider implementation for the driver.
|
||||
*
|
||||
* @param string $provider
|
||||
* @return \Illuminate\Contracts\Auth\UserProvider
|
||||
* @param string|null $provider
|
||||
* @return \Illuminate\Contracts\Auth\UserProvider|null
|
||||
*
|
||||
* @throws \InvalidArgumentException
|
||||
*/
|
||||
public function createUserProvider($provider)
|
||||
public function createUserProvider($provider = null)
|
||||
{
|
||||
$config = $this->app['config']['auth.providers.'.$provider];
|
||||
if (is_null($config = $this->getProviderConfiguration($provider))) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (isset($this->customProviderCreators[$config['driver']])) {
|
||||
if (isset($this->customProviderCreators[$driver = ($config['driver'] ?? null)])) {
|
||||
return call_user_func(
|
||||
$this->customProviderCreators[$config['driver']], $this->app, $config
|
||||
$this->customProviderCreators[$driver], $this->app, $config
|
||||
);
|
||||
}
|
||||
|
||||
switch ($config['driver']) {
|
||||
case 'database':
|
||||
return $this->createDatabaseProvider($config);
|
||||
case 'eloquent':
|
||||
return $this->createEloquentProvider($config);
|
||||
default:
|
||||
throw new InvalidArgumentException("Authentication user provider [{$config['driver']}] is not defined.");
|
||||
return match ($driver) {
|
||||
'database' => $this->createDatabaseProvider($config),
|
||||
'eloquent' => $this->createEloquentProvider($config),
|
||||
default => throw new InvalidArgumentException(
|
||||
"Authentication user provider [{$driver}] is not defined."
|
||||
),
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the user provider configuration.
|
||||
*
|
||||
* @param string|null $provider
|
||||
* @return array|null
|
||||
*/
|
||||
protected function getProviderConfiguration($provider)
|
||||
{
|
||||
if ($provider = $provider ?: $this->getDefaultUserProvider()) {
|
||||
return $this->app['config']['auth.providers.'.$provider];
|
||||
}
|
||||
}
|
||||
|
||||
@@ -49,7 +63,7 @@ trait CreatesUserProviders
|
||||
*/
|
||||
protected function createDatabaseProvider($config)
|
||||
{
|
||||
$connection = $this->app['db']->connection();
|
||||
$connection = $this->app['db']->connection($config['connection'] ?? null);
|
||||
|
||||
return new DatabaseUserProvider($connection, $this->app['hash'], $config['table']);
|
||||
}
|
||||
@@ -64,4 +78,14 @@ trait CreatesUserProviders
|
||||
{
|
||||
return new EloquentUserProvider($this->app['hash'], $config['model']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the default user provider name.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function getDefaultUserProvider()
|
||||
{
|
||||
return $this->app['config']['auth.defaults.provider'];
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,11 +2,12 @@
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Database\ConnectionInterface;
|
||||
use Illuminate\Contracts\Hashing\Hasher as HasherContract;
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Auth\Authenticatable as UserContract;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Contracts\Hashing\Hasher as HasherContract;
|
||||
use Illuminate\Contracts\Support\Arrayable;
|
||||
use Illuminate\Database\ConnectionInterface;
|
||||
|
||||
class DatabaseUserProvider implements UserProvider
|
||||
{
|
||||
@@ -15,7 +16,7 @@ class DatabaseUserProvider implements UserProvider
|
||||
*
|
||||
* @var \Illuminate\Database\ConnectionInterface
|
||||
*/
|
||||
protected $conn;
|
||||
protected $connection;
|
||||
|
||||
/**
|
||||
* The hasher implementation.
|
||||
@@ -34,14 +35,14 @@ class DatabaseUserProvider implements UserProvider
|
||||
/**
|
||||
* Create a new database user provider.
|
||||
*
|
||||
* @param \Illuminate\Database\ConnectionInterface $conn
|
||||
* @param \Illuminate\Database\ConnectionInterface $connection
|
||||
* @param \Illuminate\Contracts\Hashing\Hasher $hasher
|
||||
* @param string $table
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(ConnectionInterface $conn, HasherContract $hasher, $table)
|
||||
public function __construct(ConnectionInterface $connection, HasherContract $hasher, $table)
|
||||
{
|
||||
$this->conn = $conn;
|
||||
$this->connection = $connection;
|
||||
$this->table = $table;
|
||||
$this->hasher = $hasher;
|
||||
}
|
||||
@@ -54,7 +55,7 @@ class DatabaseUserProvider implements UserProvider
|
||||
*/
|
||||
public function retrieveById($identifier)
|
||||
{
|
||||
$user = $this->conn->table($this->table)->find($identifier);
|
||||
$user = $this->connection->table($this->table)->find($identifier);
|
||||
|
||||
return $this->getGenericUser($user);
|
||||
}
|
||||
@@ -68,12 +69,12 @@ class DatabaseUserProvider implements UserProvider
|
||||
*/
|
||||
public function retrieveByToken($identifier, $token)
|
||||
{
|
||||
$user = $this->conn->table($this->table)
|
||||
->where('id', $identifier)
|
||||
->where('remember_token', $token)
|
||||
->first();
|
||||
$user = $this->getGenericUser(
|
||||
$this->connection->table($this->table)->find($identifier)
|
||||
);
|
||||
|
||||
return $this->getGenericUser($user);
|
||||
return $user && $user->getRememberToken() && hash_equals($user->getRememberToken(), $token)
|
||||
? $user : null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -85,9 +86,9 @@ class DatabaseUserProvider implements UserProvider
|
||||
*/
|
||||
public function updateRememberToken(UserContract $user, $token)
|
||||
{
|
||||
$this->conn->table($this->table)
|
||||
->where('id', $user->getAuthIdentifier())
|
||||
->update(['remember_token' => $token]);
|
||||
$this->connection->table($this->table)
|
||||
->where($user->getAuthIdentifierName(), $user->getAuthIdentifier())
|
||||
->update([$user->getRememberTokenName() => $token]);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -98,20 +99,34 @@ class DatabaseUserProvider implements UserProvider
|
||||
*/
|
||||
public function retrieveByCredentials(array $credentials)
|
||||
{
|
||||
$credentials = array_filter(
|
||||
$credentials,
|
||||
fn ($key) => ! str_contains($key, 'password'),
|
||||
ARRAY_FILTER_USE_KEY
|
||||
);
|
||||
|
||||
if (empty($credentials)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// First we will add each credential element to the query as a where clause.
|
||||
// Then we can execute the query and, if we found a user, return it in a
|
||||
// generic "user" object that will be utilized by the Guard instances.
|
||||
$query = $this->conn->table($this->table);
|
||||
$query = $this->connection->table($this->table);
|
||||
|
||||
foreach ($credentials as $key => $value) {
|
||||
if (! Str::contains($key, 'password')) {
|
||||
if (is_array($value) || $value instanceof Arrayable) {
|
||||
$query->whereIn($key, $value);
|
||||
} elseif ($value instanceof Closure) {
|
||||
$value($query);
|
||||
} else {
|
||||
$query->where($key, $value);
|
||||
}
|
||||
}
|
||||
|
||||
// Now we are ready to execute the query to see if we have an user matching
|
||||
// the given credentials. If not, we will just return nulls and indicate
|
||||
// that there are no matching users for these given credential arrays.
|
||||
// Now we are ready to execute the query to see if we have a user matching
|
||||
// the given credentials. If not, we will just return null and indicate
|
||||
// that there are no matching users from the given credential arrays.
|
||||
$user = $query->first();
|
||||
|
||||
return $this->getGenericUser($user);
|
||||
|
||||
@@ -2,10 +2,11 @@
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Support\Str;
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Auth\Authenticatable as UserContract;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Contracts\Hashing\Hasher as HasherContract;
|
||||
use Illuminate\Contracts\Auth\Authenticatable as UserContract;
|
||||
use Illuminate\Contracts\Support\Arrayable;
|
||||
|
||||
class EloquentUserProvider implements UserProvider
|
||||
{
|
||||
@@ -23,6 +24,13 @@ class EloquentUserProvider implements UserProvider
|
||||
*/
|
||||
protected $model;
|
||||
|
||||
/**
|
||||
* The callback that may modify the user retrieval queries.
|
||||
*
|
||||
* @var (\Closure(\Illuminate\Database\Eloquent\Builder):mixed)|null
|
||||
*/
|
||||
protected $queryCallback;
|
||||
|
||||
/**
|
||||
* Create a new database user provider.
|
||||
*
|
||||
@@ -46,9 +54,9 @@ class EloquentUserProvider implements UserProvider
|
||||
{
|
||||
$model = $this->createModel();
|
||||
|
||||
return $model->newQuery()
|
||||
->where($model->getAuthIdentifierName(), $identifier)
|
||||
->first();
|
||||
return $this->newModelQuery($model)
|
||||
->where($model->getAuthIdentifierName(), $identifier)
|
||||
->first();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -62,10 +70,17 @@ class EloquentUserProvider implements UserProvider
|
||||
{
|
||||
$model = $this->createModel();
|
||||
|
||||
return $model->newQuery()
|
||||
->where($model->getAuthIdentifierName(), $identifier)
|
||||
->where($model->getRememberTokenName(), $token)
|
||||
->first();
|
||||
$retrievedModel = $this->newModelQuery($model)->where(
|
||||
$model->getAuthIdentifierName(), $identifier
|
||||
)->first();
|
||||
|
||||
if (! $retrievedModel) {
|
||||
return;
|
||||
}
|
||||
|
||||
$rememberToken = $retrievedModel->getRememberToken();
|
||||
|
||||
return $rememberToken && hash_equals($rememberToken, $token) ? $retrievedModel : null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -96,6 +111,12 @@ class EloquentUserProvider implements UserProvider
|
||||
*/
|
||||
public function retrieveByCredentials(array $credentials)
|
||||
{
|
||||
$credentials = array_filter(
|
||||
$credentials,
|
||||
fn ($key) => ! str_contains($key, 'password'),
|
||||
ARRAY_FILTER_USE_KEY
|
||||
);
|
||||
|
||||
if (empty($credentials)) {
|
||||
return;
|
||||
}
|
||||
@@ -103,10 +124,14 @@ class EloquentUserProvider implements UserProvider
|
||||
// First we will add each credential element to the query as a where clause.
|
||||
// Then we can execute the query and, if we found a user, return it in a
|
||||
// Eloquent User "model" that will be utilized by the Guard instances.
|
||||
$query = $this->createModel()->newQuery();
|
||||
$query = $this->newModelQuery();
|
||||
|
||||
foreach ($credentials as $key => $value) {
|
||||
if (! Str::contains($key, 'password')) {
|
||||
if (is_array($value) || $value instanceof Arrayable) {
|
||||
$query->whereIn($key, $value);
|
||||
} elseif ($value instanceof Closure) {
|
||||
$value($query);
|
||||
} else {
|
||||
$query->where($key, $value);
|
||||
}
|
||||
}
|
||||
@@ -128,6 +153,23 @@ class EloquentUserProvider implements UserProvider
|
||||
return $this->hasher->check($plain, $user->getAuthPassword());
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a new query builder for the model instance.
|
||||
*
|
||||
* @param \Illuminate\Database\Eloquent\Model|null $model
|
||||
* @return \Illuminate\Database\Eloquent\Builder
|
||||
*/
|
||||
protected function newModelQuery($model = null)
|
||||
{
|
||||
$query = is_null($model)
|
||||
? $this->createModel()->newQuery()
|
||||
: $model->newQuery();
|
||||
|
||||
with($query, $this->queryCallback);
|
||||
|
||||
return $query;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new instance of the model.
|
||||
*
|
||||
@@ -185,4 +227,27 @@ class EloquentUserProvider implements UserProvider
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the callback that modifies the query before retrieving users.
|
||||
*
|
||||
* @return \Closure|null
|
||||
*/
|
||||
public function getQueryCallback()
|
||||
{
|
||||
return $this->queryCallback;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the callback to modify the query before retrieving users.
|
||||
*
|
||||
* @param (\Closure(\Illuminate\Database\Eloquent\Builder):mixed)|null $queryCallback
|
||||
* @return $this
|
||||
*/
|
||||
public function withQuery($queryCallback = null)
|
||||
{
|
||||
$this->queryCallback = $queryCallback;
|
||||
|
||||
return $this;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,6 +4,13 @@ namespace Illuminate\Auth\Events;
|
||||
|
||||
class Attempting
|
||||
{
|
||||
/**
|
||||
* The authentication guard name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $guard;
|
||||
|
||||
/**
|
||||
* The credentials for the user.
|
||||
*
|
||||
@@ -21,11 +28,14 @@ class Attempting
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $guard
|
||||
* @param array $credentials
|
||||
* @param bool $remember
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($credentials, $remember)
|
||||
public function __construct($guard, $credentials, $remember)
|
||||
{
|
||||
$this->guard = $guard;
|
||||
$this->remember = $remember;
|
||||
$this->credentials = $credentials;
|
||||
}
|
||||
|
||||
@@ -8,6 +8,13 @@ class Authenticated
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The authentication guard name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $guard;
|
||||
|
||||
/**
|
||||
* The authenticated user.
|
||||
*
|
||||
@@ -18,11 +25,13 @@ class Authenticated
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $guard
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($user)
|
||||
public function __construct($guard, $user)
|
||||
{
|
||||
$this->user = $user;
|
||||
$this->guard = $guard;
|
||||
}
|
||||
}
|
||||
|
||||
37
vendor/laravel/framework/src/Illuminate/Auth/Events/CurrentDeviceLogout.php
vendored
Normal file
37
vendor/laravel/framework/src/Illuminate/Auth/Events/CurrentDeviceLogout.php
vendored
Normal file
@@ -0,0 +1,37 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Events;
|
||||
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class CurrentDeviceLogout
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The authentication guard name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $guard;
|
||||
|
||||
/**
|
||||
* The authenticated user.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Authenticatable
|
||||
*/
|
||||
public $user;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $guard
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($guard, $user)
|
||||
{
|
||||
$this->user = $user;
|
||||
$this->guard = $guard;
|
||||
}
|
||||
}
|
||||
@@ -4,6 +4,13 @@ namespace Illuminate\Auth\Events;
|
||||
|
||||
class Failed
|
||||
{
|
||||
/**
|
||||
* The authentication guard name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $guard;
|
||||
|
||||
/**
|
||||
* The user the attempter was trying to authenticate as.
|
||||
*
|
||||
@@ -21,12 +28,15 @@ class Failed
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $guard
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param array $credentials
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($user, $credentials)
|
||||
public function __construct($guard, $user, $credentials)
|
||||
{
|
||||
$this->user = $user;
|
||||
$this->guard = $guard;
|
||||
$this->credentials = $credentials;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,6 +8,13 @@ class Login
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The authentication guard name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $guard;
|
||||
|
||||
/**
|
||||
* The authenticated user.
|
||||
*
|
||||
@@ -25,13 +32,15 @@ class Login
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $guard
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param bool $remember
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($user, $remember)
|
||||
public function __construct($guard, $user, $remember)
|
||||
{
|
||||
$this->user = $user;
|
||||
$this->guard = $guard;
|
||||
$this->remember = $remember;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,6 +8,13 @@ class Logout
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The authentication guard name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $guard;
|
||||
|
||||
/**
|
||||
* The authenticated user.
|
||||
*
|
||||
@@ -18,11 +25,13 @@ class Logout
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $guard
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($user)
|
||||
public function __construct($guard, $user)
|
||||
{
|
||||
$this->user = $user;
|
||||
$this->guard = $guard;
|
||||
}
|
||||
}
|
||||
|
||||
37
vendor/laravel/framework/src/Illuminate/Auth/Events/OtherDeviceLogout.php
vendored
Normal file
37
vendor/laravel/framework/src/Illuminate/Auth/Events/OtherDeviceLogout.php
vendored
Normal file
@@ -0,0 +1,37 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Events;
|
||||
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class OtherDeviceLogout
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The authentication guard name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $guard;
|
||||
|
||||
/**
|
||||
* The authenticated user.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Authenticatable
|
||||
*/
|
||||
public $user;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $guard
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($guard, $user)
|
||||
{
|
||||
$this->user = $user;
|
||||
$this->guard = $guard;
|
||||
}
|
||||
}
|
||||
28
vendor/laravel/framework/src/Illuminate/Auth/Events/PasswordReset.php
vendored
Normal file
28
vendor/laravel/framework/src/Illuminate/Auth/Events/PasswordReset.php
vendored
Normal file
@@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Events;
|
||||
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class PasswordReset
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The user.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Authenticatable
|
||||
*/
|
||||
public $user;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($user)
|
||||
{
|
||||
$this->user = $user;
|
||||
}
|
||||
}
|
||||
37
vendor/laravel/framework/src/Illuminate/Auth/Events/Validated.php
vendored
Normal file
37
vendor/laravel/framework/src/Illuminate/Auth/Events/Validated.php
vendored
Normal file
@@ -0,0 +1,37 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Events;
|
||||
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class Validated
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The authentication guard name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $guard;
|
||||
|
||||
/**
|
||||
* The user retrieved and validated from the User Provider.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Authenticatable
|
||||
*/
|
||||
public $user;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $guard
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($guard, $user)
|
||||
{
|
||||
$this->user = $user;
|
||||
$this->guard = $guard;
|
||||
}
|
||||
}
|
||||
28
vendor/laravel/framework/src/Illuminate/Auth/Events/Verified.php
vendored
Normal file
28
vendor/laravel/framework/src/Illuminate/Auth/Events/Verified.php
vendored
Normal file
@@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Events;
|
||||
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class Verified
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The verified user.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\MustVerifyEmail
|
||||
*/
|
||||
public $user;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\MustVerifyEmail $user
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($user)
|
||||
{
|
||||
$this->user = $user;
|
||||
}
|
||||
}
|
||||
@@ -41,9 +41,7 @@ class GenericUser implements UserContract
|
||||
*/
|
||||
public function getAuthIdentifier()
|
||||
{
|
||||
$name = $this->getAuthIdentifierName();
|
||||
|
||||
return $this->attributes[$name];
|
||||
return $this->attributes[$this->getAuthIdentifierName()];
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Contracts\Auth\Authenticatable as AuthenticatableContract;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
|
||||
/**
|
||||
* These methods are typically the same across all guards.
|
||||
@@ -24,7 +25,7 @@ trait GuardHelpers
|
||||
protected $provider;
|
||||
|
||||
/**
|
||||
* Determine if the current user is authenticated.
|
||||
* Determine if the current user is authenticated. If not, throw an exception.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable
|
||||
*
|
||||
@@ -39,6 +40,16 @@ trait GuardHelpers
|
||||
throw new AuthenticationException;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the guard has a user instance.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function hasUser()
|
||||
{
|
||||
return ! is_null($this->user);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the current user is authenticated.
|
||||
*
|
||||
@@ -62,7 +73,7 @@ trait GuardHelpers
|
||||
/**
|
||||
* Get the ID for the currently authenticated user.
|
||||
*
|
||||
* @return int|null
|
||||
* @return int|string|null
|
||||
*/
|
||||
public function id()
|
||||
{
|
||||
@@ -83,4 +94,37 @@ trait GuardHelpers
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Forget the current user.
|
||||
*
|
||||
* @return $this
|
||||
*/
|
||||
public function forgetUser()
|
||||
{
|
||||
$this->user = null;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the user provider used by the guard.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Auth\UserProvider
|
||||
*/
|
||||
public function getProvider()
|
||||
{
|
||||
return $this->provider;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the user provider used by the guard.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\UserProvider $provider
|
||||
* @return void
|
||||
*/
|
||||
public function setProvider(UserProvider $provider)
|
||||
{
|
||||
$this->provider = $provider;
|
||||
}
|
||||
}
|
||||
|
||||
21
vendor/laravel/framework/src/Illuminate/Auth/LICENSE.md
vendored
Normal file
21
vendor/laravel/framework/src/Illuminate/Auth/LICENSE.md
vendored
Normal file
@@ -0,0 +1,21 @@
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) Taylor Otwell
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
22
vendor/laravel/framework/src/Illuminate/Auth/Listeners/SendEmailVerificationNotification.php
vendored
Normal file
22
vendor/laravel/framework/src/Illuminate/Auth/Listeners/SendEmailVerificationNotification.php
vendored
Normal file
@@ -0,0 +1,22 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Listeners;
|
||||
|
||||
use Illuminate\Auth\Events\Registered;
|
||||
use Illuminate\Contracts\Auth\MustVerifyEmail;
|
||||
|
||||
class SendEmailVerificationNotification
|
||||
{
|
||||
/**
|
||||
* Handle the event.
|
||||
*
|
||||
* @param \Illuminate\Auth\Events\Registered $event
|
||||
* @return void
|
||||
*/
|
||||
public function handle(Registered $event)
|
||||
{
|
||||
if ($event->user instanceof MustVerifyEmail && ! $event->user->hasVerifiedEmail()) {
|
||||
$event->user->sendEmailVerificationNotification();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -5,8 +5,9 @@ namespace Illuminate\Auth\Middleware;
|
||||
use Closure;
|
||||
use Illuminate\Auth\AuthenticationException;
|
||||
use Illuminate\Contracts\Auth\Factory as Auth;
|
||||
use Illuminate\Contracts\Auth\Middleware\AuthenticatesRequests;
|
||||
|
||||
class Authenticate
|
||||
class Authenticate implements AuthenticatesRequests
|
||||
{
|
||||
/**
|
||||
* The authentication factory instance.
|
||||
@@ -38,7 +39,7 @@ class Authenticate
|
||||
*/
|
||||
public function handle($request, Closure $next, ...$guards)
|
||||
{
|
||||
$this->authenticate($guards);
|
||||
$this->authenticate($request, $guards);
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
@@ -46,15 +47,16 @@ class Authenticate
|
||||
/**
|
||||
* Determine if the user is logged in to any of the given guards.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param array $guards
|
||||
* @return void
|
||||
*
|
||||
* @throws \Illuminate\Auth\AuthenticationException
|
||||
*/
|
||||
protected function authenticate(array $guards)
|
||||
protected function authenticate($request, array $guards)
|
||||
{
|
||||
if (empty($guards)) {
|
||||
return $this->auth->authenticate();
|
||||
$guards = [null];
|
||||
}
|
||||
|
||||
foreach ($guards as $guard) {
|
||||
@@ -63,6 +65,33 @@ class Authenticate
|
||||
}
|
||||
}
|
||||
|
||||
throw new AuthenticationException('Unauthenticated.', $guards);
|
||||
$this->unauthenticated($request, $guards);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle an unauthenticated user.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param array $guards
|
||||
* @return void
|
||||
*
|
||||
* @throws \Illuminate\Auth\AuthenticationException
|
||||
*/
|
||||
protected function unauthenticated($request, array $guards)
|
||||
{
|
||||
throw new AuthenticationException(
|
||||
'Unauthenticated.', $guards, $this->redirectTo($request)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the path the user should be redirected to when they are not authenticated.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return string|null
|
||||
*/
|
||||
protected function redirectTo($request)
|
||||
{
|
||||
//
|
||||
}
|
||||
}
|
||||
|
||||
@@ -31,10 +31,15 @@ class AuthenticateWithBasicAuth
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @param string|null $guard
|
||||
* @param string|null $field
|
||||
* @return mixed
|
||||
*
|
||||
* @throws \Symfony\Component\HttpKernel\Exception\UnauthorizedHttpException
|
||||
*/
|
||||
public function handle($request, Closure $next, $guard = null)
|
||||
public function handle($request, Closure $next, $guard = null, $field = null)
|
||||
{
|
||||
return $this->auth->guard($guard)->basic() ?: $next($request);
|
||||
$this->auth->guard($guard)->basic($field ?: 'email');
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,19 +3,11 @@
|
||||
namespace Illuminate\Auth\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
use Illuminate\Contracts\Auth\Access\Gate;
|
||||
use Illuminate\Contracts\Auth\Factory as Auth;
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
|
||||
class Authorize
|
||||
{
|
||||
/**
|
||||
* The authentication factory instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Factory
|
||||
*/
|
||||
protected $auth;
|
||||
|
||||
/**
|
||||
* The gate instance.
|
||||
*
|
||||
@@ -26,13 +18,11 @@ class Authorize
|
||||
/**
|
||||
* Create a new middleware instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Factory $auth
|
||||
* @param \Illuminate\Contracts\Auth\Access\Gate $gate
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Auth $auth, Gate $gate)
|
||||
public function __construct(Gate $gate)
|
||||
{
|
||||
$this->auth = $auth;
|
||||
$this->gate = $gate;
|
||||
}
|
||||
|
||||
@@ -42,7 +32,7 @@ class Authorize
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @param string $ability
|
||||
* @param array|null $models
|
||||
* @param array|null ...$models
|
||||
* @return mixed
|
||||
*
|
||||
* @throws \Illuminate\Auth\AuthenticationException
|
||||
@@ -50,8 +40,6 @@ class Authorize
|
||||
*/
|
||||
public function handle($request, Closure $next, $ability, ...$models)
|
||||
{
|
||||
$this->auth->authenticate();
|
||||
|
||||
$this->gate->authorize($ability, $this->getGateArguments($request, $models));
|
||||
|
||||
return $next($request);
|
||||
@@ -62,7 +50,7 @@ class Authorize
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param array|null $models
|
||||
* @return array|string|\Illuminate\Database\Eloquent\Model
|
||||
* @return \Illuminate\Database\Eloquent\Model|array|string
|
||||
*/
|
||||
protected function getGateArguments($request, $models)
|
||||
{
|
||||
@@ -80,11 +68,16 @@ class Authorize
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param string $model
|
||||
* @return string|\Illuminate\Database\Eloquent\Model
|
||||
* @return \Illuminate\Database\Eloquent\Model|string
|
||||
*/
|
||||
protected function getModel($request, $model)
|
||||
{
|
||||
return $this->isClassName($model) ? $model : $request->route($model);
|
||||
if ($this->isClassName($model)) {
|
||||
return trim($model);
|
||||
} else {
|
||||
return $request->route($model, null) ??
|
||||
((preg_match("/^['\"](.*)['\"]$/", trim($model), $matches)) ? $matches[1] : null);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -95,6 +88,6 @@ class Authorize
|
||||
*/
|
||||
protected function isClassName($value)
|
||||
{
|
||||
return strpos($value, '\\') !== false;
|
||||
return str_contains($value, '\\');
|
||||
}
|
||||
}
|
||||
|
||||
32
vendor/laravel/framework/src/Illuminate/Auth/Middleware/EnsureEmailIsVerified.php
vendored
Normal file
32
vendor/laravel/framework/src/Illuminate/Auth/Middleware/EnsureEmailIsVerified.php
vendored
Normal file
@@ -0,0 +1,32 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Auth\MustVerifyEmail;
|
||||
use Illuminate\Support\Facades\Redirect;
|
||||
use Illuminate\Support\Facades\URL;
|
||||
|
||||
class EnsureEmailIsVerified
|
||||
{
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @param string|null $redirectToRoute
|
||||
* @return \Illuminate\Http\Response|\Illuminate\Http\RedirectResponse|null
|
||||
*/
|
||||
public function handle($request, Closure $next, $redirectToRoute = null)
|
||||
{
|
||||
if (! $request->user() ||
|
||||
($request->user() instanceof MustVerifyEmail &&
|
||||
! $request->user()->hasVerifiedEmail())) {
|
||||
return $request->expectsJson()
|
||||
? abort(403, 'Your email address is not verified.')
|
||||
: Redirect::guest(URL::route($redirectToRoute ?: 'verification.notice'));
|
||||
}
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
}
|
||||
86
vendor/laravel/framework/src/Illuminate/Auth/Middleware/RequirePassword.php
vendored
Normal file
86
vendor/laravel/framework/src/Illuminate/Auth/Middleware/RequirePassword.php
vendored
Normal file
@@ -0,0 +1,86 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Routing\ResponseFactory;
|
||||
use Illuminate\Contracts\Routing\UrlGenerator;
|
||||
|
||||
class RequirePassword
|
||||
{
|
||||
/**
|
||||
* The response factory instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Routing\ResponseFactory
|
||||
*/
|
||||
protected $responseFactory;
|
||||
|
||||
/**
|
||||
* The URL generator instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Routing\UrlGenerator
|
||||
*/
|
||||
protected $urlGenerator;
|
||||
|
||||
/**
|
||||
* The password timeout.
|
||||
*
|
||||
* @var int
|
||||
*/
|
||||
protected $passwordTimeout;
|
||||
|
||||
/**
|
||||
* Create a new middleware instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Routing\ResponseFactory $responseFactory
|
||||
* @param \Illuminate\Contracts\Routing\UrlGenerator $urlGenerator
|
||||
* @param int|null $passwordTimeout
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(ResponseFactory $responseFactory, UrlGenerator $urlGenerator, $passwordTimeout = null)
|
||||
{
|
||||
$this->responseFactory = $responseFactory;
|
||||
$this->urlGenerator = $urlGenerator;
|
||||
$this->passwordTimeout = $passwordTimeout ?: 10800;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @param string|null $redirectToRoute
|
||||
* @param int|null $passwordTimeoutSeconds
|
||||
* @return mixed
|
||||
*/
|
||||
public function handle($request, Closure $next, $redirectToRoute = null, $passwordTimeoutSeconds = null)
|
||||
{
|
||||
if ($this->shouldConfirmPassword($request, $passwordTimeoutSeconds)) {
|
||||
if ($request->expectsJson()) {
|
||||
return $this->responseFactory->json([
|
||||
'message' => 'Password confirmation required.',
|
||||
], 423);
|
||||
}
|
||||
|
||||
return $this->responseFactory->redirectGuest(
|
||||
$this->urlGenerator->route($redirectToRoute ?? 'password.confirm')
|
||||
);
|
||||
}
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the confirmation timeout has expired.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param int|null $passwordTimeoutSeconds
|
||||
* @return bool
|
||||
*/
|
||||
protected function shouldConfirmPassword($request, $passwordTimeoutSeconds = null)
|
||||
{
|
||||
$confirmedAt = time() - $request->session()->get('auth.password_confirmed_at', 0);
|
||||
|
||||
return $confirmedAt > ($passwordTimeoutSeconds ?? $this->passwordTimeout);
|
||||
}
|
||||
}
|
||||
50
vendor/laravel/framework/src/Illuminate/Auth/MustVerifyEmail.php
vendored
Normal file
50
vendor/laravel/framework/src/Illuminate/Auth/MustVerifyEmail.php
vendored
Normal file
@@ -0,0 +1,50 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Auth\Notifications\VerifyEmail;
|
||||
|
||||
trait MustVerifyEmail
|
||||
{
|
||||
/**
|
||||
* Determine if the user has verified their email address.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function hasVerifiedEmail()
|
||||
{
|
||||
return ! is_null($this->email_verified_at);
|
||||
}
|
||||
|
||||
/**
|
||||
* Mark the given user's email as verified.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function markEmailAsVerified()
|
||||
{
|
||||
return $this->forceFill([
|
||||
'email_verified_at' => $this->freshTimestamp(),
|
||||
])->save();
|
||||
}
|
||||
|
||||
/**
|
||||
* Send the email verification notification.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function sendEmailVerificationNotification()
|
||||
{
|
||||
$this->notify(new VerifyEmail);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the email address that should be used for verification.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function getEmailForVerification()
|
||||
{
|
||||
return $this->email;
|
||||
}
|
||||
}
|
||||
@@ -2,8 +2,9 @@
|
||||
|
||||
namespace Illuminate\Auth\Notifications;
|
||||
|
||||
use Illuminate\Notifications\Notification;
|
||||
use Illuminate\Notifications\Messages\MailMessage;
|
||||
use Illuminate\Notifications\Notification;
|
||||
use Illuminate\Support\Facades\Lang;
|
||||
|
||||
class ResetPassword extends Notification
|
||||
{
|
||||
@@ -14,6 +15,20 @@ class ResetPassword extends Notification
|
||||
*/
|
||||
public $token;
|
||||
|
||||
/**
|
||||
* The callback that should be used to create the reset password URL.
|
||||
*
|
||||
* @var (\Closure(mixed, string): string)|null
|
||||
*/
|
||||
public static $createUrlCallback;
|
||||
|
||||
/**
|
||||
* The callback that should be used to build the mail message.
|
||||
*
|
||||
* @var (\Closure(mixed, string): \Illuminate\Notifications\Messages\MailMessage)|null
|
||||
*/
|
||||
public static $toMailCallback;
|
||||
|
||||
/**
|
||||
* Create a notification instance.
|
||||
*
|
||||
@@ -43,10 +58,67 @@ class ResetPassword extends Notification
|
||||
* @return \Illuminate\Notifications\Messages\MailMessage
|
||||
*/
|
||||
public function toMail($notifiable)
|
||||
{
|
||||
if (static::$toMailCallback) {
|
||||
return call_user_func(static::$toMailCallback, $notifiable, $this->token);
|
||||
}
|
||||
|
||||
return $this->buildMailMessage($this->resetUrl($notifiable));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the reset password notification mail message for the given URL.
|
||||
*
|
||||
* @param string $url
|
||||
* @return \Illuminate\Notifications\Messages\MailMessage
|
||||
*/
|
||||
protected function buildMailMessage($url)
|
||||
{
|
||||
return (new MailMessage)
|
||||
->line('You are receiving this email because we received a password reset request for your account.')
|
||||
->action('Reset Password', url(config('app.url').route('password.reset', $this->token, false)))
|
||||
->line('If you did not request a password reset, no further action is required.');
|
||||
->subject(Lang::get('Reset Password Notification'))
|
||||
->line(Lang::get('You are receiving this email because we received a password reset request for your account.'))
|
||||
->action(Lang::get('Reset Password'), $url)
|
||||
->line(Lang::get('This password reset link will expire in :count minutes.', ['count' => config('auth.passwords.'.config('auth.defaults.passwords').'.expire')]))
|
||||
->line(Lang::get('If you did not request a password reset, no further action is required.'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the reset URL for the given notifiable.
|
||||
*
|
||||
* @param mixed $notifiable
|
||||
* @return string
|
||||
*/
|
||||
protected function resetUrl($notifiable)
|
||||
{
|
||||
if (static::$createUrlCallback) {
|
||||
return call_user_func(static::$createUrlCallback, $notifiable, $this->token);
|
||||
}
|
||||
|
||||
return url(route('password.reset', [
|
||||
'token' => $this->token,
|
||||
'email' => $notifiable->getEmailForPasswordReset(),
|
||||
], false));
|
||||
}
|
||||
|
||||
/**
|
||||
* Set a callback that should be used when creating the reset password button URL.
|
||||
*
|
||||
* @param \Closure(mixed, string): string $callback
|
||||
* @return void
|
||||
*/
|
||||
public static function createUrlUsing($callback)
|
||||
{
|
||||
static::$createUrlCallback = $callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set a callback that should be used when building the notification mail message.
|
||||
*
|
||||
* @param \Closure(mixed, string): \Illuminate\Notifications\Messages\MailMessage $callback
|
||||
* @return void
|
||||
*/
|
||||
public static function toMailUsing($callback)
|
||||
{
|
||||
static::$toMailCallback = $callback;
|
||||
}
|
||||
}
|
||||
|
||||
114
vendor/laravel/framework/src/Illuminate/Auth/Notifications/VerifyEmail.php
vendored
Normal file
114
vendor/laravel/framework/src/Illuminate/Auth/Notifications/VerifyEmail.php
vendored
Normal file
@@ -0,0 +1,114 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Notifications;
|
||||
|
||||
use Illuminate\Notifications\Messages\MailMessage;
|
||||
use Illuminate\Notifications\Notification;
|
||||
use Illuminate\Support\Carbon;
|
||||
use Illuminate\Support\Facades\Config;
|
||||
use Illuminate\Support\Facades\Lang;
|
||||
use Illuminate\Support\Facades\URL;
|
||||
|
||||
class VerifyEmail extends Notification
|
||||
{
|
||||
/**
|
||||
* The callback that should be used to create the verify email URL.
|
||||
*
|
||||
* @var \Closure|null
|
||||
*/
|
||||
public static $createUrlCallback;
|
||||
|
||||
/**
|
||||
* The callback that should be used to build the mail message.
|
||||
*
|
||||
* @var \Closure|null
|
||||
*/
|
||||
public static $toMailCallback;
|
||||
|
||||
/**
|
||||
* Get the notification's channels.
|
||||
*
|
||||
* @param mixed $notifiable
|
||||
* @return array|string
|
||||
*/
|
||||
public function via($notifiable)
|
||||
{
|
||||
return ['mail'];
|
||||
}
|
||||
|
||||
/**
|
||||
* Build the mail representation of the notification.
|
||||
*
|
||||
* @param mixed $notifiable
|
||||
* @return \Illuminate\Notifications\Messages\MailMessage
|
||||
*/
|
||||
public function toMail($notifiable)
|
||||
{
|
||||
$verificationUrl = $this->verificationUrl($notifiable);
|
||||
|
||||
if (static::$toMailCallback) {
|
||||
return call_user_func(static::$toMailCallback, $notifiable, $verificationUrl);
|
||||
}
|
||||
|
||||
return $this->buildMailMessage($verificationUrl);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the verify email notification mail message for the given URL.
|
||||
*
|
||||
* @param string $url
|
||||
* @return \Illuminate\Notifications\Messages\MailMessage
|
||||
*/
|
||||
protected function buildMailMessage($url)
|
||||
{
|
||||
return (new MailMessage)
|
||||
->subject(Lang::get('Verify Email Address'))
|
||||
->line(Lang::get('Please click the button below to verify your email address.'))
|
||||
->action(Lang::get('Verify Email Address'), $url)
|
||||
->line(Lang::get('If you did not create an account, no further action is required.'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the verification URL for the given notifiable.
|
||||
*
|
||||
* @param mixed $notifiable
|
||||
* @return string
|
||||
*/
|
||||
protected function verificationUrl($notifiable)
|
||||
{
|
||||
if (static::$createUrlCallback) {
|
||||
return call_user_func(static::$createUrlCallback, $notifiable);
|
||||
}
|
||||
|
||||
return URL::temporarySignedRoute(
|
||||
'verification.verify',
|
||||
Carbon::now()->addMinutes(Config::get('auth.verification.expire', 60)),
|
||||
[
|
||||
'id' => $notifiable->getKey(),
|
||||
'hash' => sha1($notifiable->getEmailForVerification()),
|
||||
]
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set a callback that should be used when creating the email verification URL.
|
||||
*
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public static function createUrlUsing($callback)
|
||||
{
|
||||
static::$createUrlCallback = $callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set a callback that should be used when building the notification mail message.
|
||||
*
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public static function toMailUsing($callback)
|
||||
{
|
||||
static::$toMailCallback = $callback;
|
||||
}
|
||||
}
|
||||
@@ -2,11 +2,11 @@
|
||||
|
||||
namespace Illuminate\Auth\Passwords;
|
||||
|
||||
use Carbon\Carbon;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Database\ConnectionInterface;
|
||||
use Illuminate\Contracts\Hashing\Hasher as HasherContract;
|
||||
use Illuminate\Contracts\Auth\CanResetPassword as CanResetPasswordContract;
|
||||
use Illuminate\Contracts\Hashing\Hasher as HasherContract;
|
||||
use Illuminate\Database\ConnectionInterface;
|
||||
use Illuminate\Support\Carbon;
|
||||
use Illuminate\Support\Str;
|
||||
|
||||
class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
{
|
||||
@@ -45,6 +45,13 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
*/
|
||||
protected $expires;
|
||||
|
||||
/**
|
||||
* Minimum number of seconds before re-redefining the token.
|
||||
*
|
||||
* @var int
|
||||
*/
|
||||
protected $throttle;
|
||||
|
||||
/**
|
||||
* Create a new token repository instance.
|
||||
*
|
||||
@@ -53,16 +60,19 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
* @param string $table
|
||||
* @param string $hashKey
|
||||
* @param int $expires
|
||||
* @param int $throttle
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(ConnectionInterface $connection, HasherContract $hasher,
|
||||
$table, $hashKey, $expires = 60)
|
||||
$table, $hashKey, $expires = 60,
|
||||
$throttle = 60)
|
||||
{
|
||||
$this->table = $table;
|
||||
$this->hasher = $hasher;
|
||||
$this->hashKey = $hashKey;
|
||||
$this->expires = $expires * 60;
|
||||
$this->connection = $connection;
|
||||
$this->throttle = $throttle;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -139,6 +149,38 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
return Carbon::parse($createdAt)->addSeconds($this->expires)->isPast();
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the given user recently created a password reset token.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @return bool
|
||||
*/
|
||||
public function recentlyCreatedToken(CanResetPasswordContract $user)
|
||||
{
|
||||
$record = (array) $this->getTable()->where(
|
||||
'email', $user->getEmailForPasswordReset()
|
||||
)->first();
|
||||
|
||||
return $record && $this->tokenRecentlyCreated($record['created_at']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the token was recently created.
|
||||
*
|
||||
* @param string $createdAt
|
||||
* @return bool
|
||||
*/
|
||||
protected function tokenRecentlyCreated($createdAt)
|
||||
{
|
||||
if ($this->throttle <= 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return Carbon::parse($createdAt)->addSeconds(
|
||||
$this->throttle
|
||||
)->isFuture();
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete a token record by user.
|
||||
*
|
||||
|
||||
@@ -3,11 +3,11 @@
|
||||
namespace Illuminate\Auth\Passwords;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Auth\CanResetPassword as CanResetPasswordContract;
|
||||
use Illuminate\Contracts\Auth\PasswordBroker as PasswordBrokerContract;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Support\Arr;
|
||||
use UnexpectedValueException;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Contracts\Auth\PasswordBroker as PasswordBrokerContract;
|
||||
use Illuminate\Contracts\Auth\CanResetPassword as CanResetPasswordContract;
|
||||
|
||||
class PasswordBroker implements PasswordBrokerContract
|
||||
{
|
||||
@@ -25,13 +25,6 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
*/
|
||||
protected $users;
|
||||
|
||||
/**
|
||||
* The custom password validator callback.
|
||||
*
|
||||
* @var \Closure
|
||||
*/
|
||||
protected $passwordValidator;
|
||||
|
||||
/**
|
||||
* Create a new password broker instance.
|
||||
*
|
||||
@@ -39,8 +32,7 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
* @param \Illuminate\Contracts\Auth\UserProvider $users
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(TokenRepositoryInterface $tokens,
|
||||
UserProvider $users)
|
||||
public function __construct(TokenRepositoryInterface $tokens, UserProvider $users)
|
||||
{
|
||||
$this->users = $users;
|
||||
$this->tokens = $tokens;
|
||||
@@ -50,9 +42,10 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
* Send a password reset link to a user.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @param \Closure|null $callback
|
||||
* @return string
|
||||
*/
|
||||
public function sendResetLink(array $credentials)
|
||||
public function sendResetLink(array $credentials, Closure $callback = null)
|
||||
{
|
||||
// First we will check to see if we found a user at the given credentials and
|
||||
// if we did not we will redirect back to this current URI with a piece of
|
||||
@@ -63,12 +56,20 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
return static::INVALID_USER;
|
||||
}
|
||||
|
||||
// Once we have the reset token, we are ready to send the message out to this
|
||||
// user with a link to reset their password. We will then redirect back to
|
||||
// the current URI having nothing set in the session to indicate errors.
|
||||
$user->sendPasswordResetNotification(
|
||||
$this->tokens->create($user)
|
||||
);
|
||||
if ($this->tokens->recentlyCreatedToken($user)) {
|
||||
return static::RESET_THROTTLED;
|
||||
}
|
||||
|
||||
$token = $this->tokens->create($user);
|
||||
|
||||
if ($callback) {
|
||||
$callback($user, $token);
|
||||
} else {
|
||||
// Once we have the reset token, we are ready to send the message out to this
|
||||
// user with a link to reset their password. We will then redirect back to
|
||||
// the current URI having nothing set in the session to indicate errors.
|
||||
$user->sendPasswordResetNotification($token);
|
||||
}
|
||||
|
||||
return static::RESET_LINK_SENT;
|
||||
}
|
||||
@@ -82,11 +83,11 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
*/
|
||||
public function reset(array $credentials, Closure $callback)
|
||||
{
|
||||
$user = $this->validateReset($credentials);
|
||||
|
||||
// If the responses from the validate method is not a user instance, we will
|
||||
// assume that it is a redirect and simply return it from this method and
|
||||
// the user is properly redirected having an error message on the post.
|
||||
$user = $this->validateReset($credentials);
|
||||
|
||||
if (! $user instanceof CanResetPasswordContract) {
|
||||
return $user;
|
||||
}
|
||||
@@ -107,7 +108,7 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
* Validate a password reset for the given credentials.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @return \Illuminate\Contracts\Auth\CanResetPassword
|
||||
* @return \Illuminate\Contracts\Auth\CanResetPassword|string
|
||||
*/
|
||||
protected function validateReset(array $credentials)
|
||||
{
|
||||
@@ -115,10 +116,6 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
return static::INVALID_USER;
|
||||
}
|
||||
|
||||
if (! $this->validateNewPassword($credentials)) {
|
||||
return static::INVALID_PASSWORD;
|
||||
}
|
||||
|
||||
if (! $this->tokens->exists($user, $credentials['token'])) {
|
||||
return static::INVALID_TOKEN;
|
||||
}
|
||||
@@ -126,60 +123,11 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
return $user;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set a custom password validator.
|
||||
*
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public function validator(Closure $callback)
|
||||
{
|
||||
$this->passwordValidator = $callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the passwords match for the request.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @return bool
|
||||
*/
|
||||
public function validateNewPassword(array $credentials)
|
||||
{
|
||||
if (isset($this->passwordValidator)) {
|
||||
list($password, $confirm) = [
|
||||
$credentials['password'],
|
||||
$credentials['password_confirmation'],
|
||||
];
|
||||
|
||||
return call_user_func(
|
||||
$this->passwordValidator, $credentials
|
||||
) && $password === $confirm;
|
||||
}
|
||||
|
||||
return $this->validatePasswordWithDefaults($credentials);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the passwords are valid for the request.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @return bool
|
||||
*/
|
||||
protected function validatePasswordWithDefaults(array $credentials)
|
||||
{
|
||||
list($password, $confirm) = [
|
||||
$credentials['password'],
|
||||
$credentials['password_confirmation'],
|
||||
];
|
||||
|
||||
return $password === $confirm && mb_strlen($password) >= 6;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the user for the given credentials.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @return \Illuminate\Contracts\Auth\CanResetPassword
|
||||
* @return \Illuminate\Contracts\Auth\CanResetPassword|null
|
||||
*
|
||||
* @throws \UnexpectedValueException
|
||||
*/
|
||||
@@ -199,7 +147,7 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
/**
|
||||
* Create a new password reset token for the given user.
|
||||
*
|
||||
* @param CanResetPasswordContract $user
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @return string
|
||||
*/
|
||||
public function createToken(CanResetPasswordContract $user)
|
||||
@@ -210,7 +158,7 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
/**
|
||||
* Delete password reset tokens of the given user.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @return void
|
||||
*/
|
||||
public function deleteToken(CanResetPasswordContract $user)
|
||||
@@ -221,8 +169,8 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
/**
|
||||
* Validate the given password reset token.
|
||||
*
|
||||
* @param CanResetPasswordContract $user
|
||||
* @param string $token
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @param string $token
|
||||
* @return bool
|
||||
*/
|
||||
public function tokenExists(CanResetPasswordContract $user, $token)
|
||||
|
||||
@@ -2,16 +2,18 @@
|
||||
|
||||
namespace Illuminate\Auth\Passwords;
|
||||
|
||||
use Illuminate\Support\Str;
|
||||
use InvalidArgumentException;
|
||||
use Illuminate\Contracts\Auth\PasswordBrokerFactory as FactoryContract;
|
||||
use InvalidArgumentException;
|
||||
|
||||
/**
|
||||
* @mixin \Illuminate\Contracts\Auth\PasswordBroker
|
||||
*/
|
||||
class PasswordBrokerManager implements FactoryContract
|
||||
{
|
||||
/**
|
||||
* The application instance.
|
||||
*
|
||||
* @var \Illuminate\Foundation\Application
|
||||
* @var \Illuminate\Contracts\Foundation\Application
|
||||
*/
|
||||
protected $app;
|
||||
|
||||
@@ -25,7 +27,7 @@ class PasswordBrokerManager implements FactoryContract
|
||||
/**
|
||||
* Create a new PasswordBroker manager instance.
|
||||
*
|
||||
* @param \Illuminate\Foundation\Application $app
|
||||
* @param \Illuminate\Contracts\Foundation\Application $app
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($app)
|
||||
@@ -36,16 +38,14 @@ class PasswordBrokerManager implements FactoryContract
|
||||
/**
|
||||
* Attempt to get the broker from the local cache.
|
||||
*
|
||||
* @param string $name
|
||||
* @param string|null $name
|
||||
* @return \Illuminate\Contracts\Auth\PasswordBroker
|
||||
*/
|
||||
public function broker($name = null)
|
||||
{
|
||||
$name = $name ?: $this->getDefaultDriver();
|
||||
|
||||
return isset($this->brokers[$name])
|
||||
? $this->brokers[$name]
|
||||
: $this->brokers[$name] = $this->resolve($name);
|
||||
return $this->brokers[$name] ?? ($this->brokers[$name] = $this->resolve($name));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -69,7 +69,7 @@ class PasswordBrokerManager implements FactoryContract
|
||||
// aggregate service of sorts providing a convenient interface for resets.
|
||||
return new PasswordBroker(
|
||||
$this->createTokenRepository($config),
|
||||
$this->app['auth']->createUserProvider($config['provider'])
|
||||
$this->app['auth']->createUserProvider($config['provider'] ?? null)
|
||||
);
|
||||
}
|
||||
|
||||
@@ -83,18 +83,19 @@ class PasswordBrokerManager implements FactoryContract
|
||||
{
|
||||
$key = $this->app['config']['app.key'];
|
||||
|
||||
if (Str::startsWith($key, 'base64:')) {
|
||||
if (str_starts_with($key, 'base64:')) {
|
||||
$key = base64_decode(substr($key, 7));
|
||||
}
|
||||
|
||||
$connection = isset($config['connection']) ? $config['connection'] : null;
|
||||
$connection = $config['connection'] ?? null;
|
||||
|
||||
return new DatabaseTokenRepository(
|
||||
$this->app['db']->connection($connection),
|
||||
$this->app['hash'],
|
||||
$config['table'],
|
||||
$key,
|
||||
$config['expire']
|
||||
$config['expire'],
|
||||
$config['throttle'] ?? 0
|
||||
);
|
||||
}
|
||||
|
||||
@@ -134,7 +135,7 @@ class PasswordBrokerManager implements FactoryContract
|
||||
* Dynamically call the default driver instance.
|
||||
*
|
||||
* @param string $method
|
||||
* @param array $parameters
|
||||
* @param array $parameters
|
||||
* @return mixed
|
||||
*/
|
||||
public function __call($method, $parameters)
|
||||
|
||||
@@ -2,17 +2,11 @@
|
||||
|
||||
namespace Illuminate\Auth\Passwords;
|
||||
|
||||
use Illuminate\Contracts\Support\DeferrableProvider;
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
|
||||
class PasswordResetServiceProvider extends ServiceProvider
|
||||
class PasswordResetServiceProvider extends ServiceProvider implements DeferrableProvider
|
||||
{
|
||||
/**
|
||||
* Indicates if loading of the provider is deferred.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
protected $defer = true;
|
||||
|
||||
/**
|
||||
* Register the service provider.
|
||||
*
|
||||
|
||||
@@ -23,6 +23,14 @@ interface TokenRepositoryInterface
|
||||
*/
|
||||
public function exists(CanResetPasswordContract $user, $token);
|
||||
|
||||
/**
|
||||
* Determine if the given user recently created a password reset token.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @return bool
|
||||
*/
|
||||
public function recentlyCreatedToken(CanResetPasswordContract $user);
|
||||
|
||||
/**
|
||||
* Delete a token record.
|
||||
*
|
||||
|
||||
@@ -2,8 +2,6 @@
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Support\Str;
|
||||
|
||||
class Recaller
|
||||
{
|
||||
/**
|
||||
@@ -21,7 +19,7 @@ class Recaller
|
||||
*/
|
||||
public function __construct($recaller)
|
||||
{
|
||||
$this->recaller = $recaller;
|
||||
$this->recaller = @unserialize($recaller, ['allowed_classes' => false]) ?: $recaller;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -31,7 +29,7 @@ class Recaller
|
||||
*/
|
||||
public function id()
|
||||
{
|
||||
return explode('|', $this->recaller, 2)[0];
|
||||
return explode('|', $this->recaller, 3)[0];
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -41,7 +39,17 @@ class Recaller
|
||||
*/
|
||||
public function token()
|
||||
{
|
||||
return explode('|', $this->recaller, 2)[1];
|
||||
return explode('|', $this->recaller, 3)[1];
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the password from the recaller.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function hash()
|
||||
{
|
||||
return explode('|', $this->recaller, 4)[2];
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -51,7 +59,7 @@ class Recaller
|
||||
*/
|
||||
public function valid()
|
||||
{
|
||||
return $this->properString() && $this->hasBothSegments();
|
||||
return $this->properString() && $this->hasAllSegments();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -61,18 +69,28 @@ class Recaller
|
||||
*/
|
||||
protected function properString()
|
||||
{
|
||||
return is_string($this->recaller) && Str::contains($this->recaller, '|');
|
||||
return is_string($this->recaller) && str_contains($this->recaller, '|');
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the recaller has both segments.
|
||||
* Determine if the recaller has all segments.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
protected function hasBothSegments()
|
||||
protected function hasAllSegments()
|
||||
{
|
||||
$segments = explode('|', $this->recaller);
|
||||
|
||||
return count($segments) == 2 && trim($segments[0]) !== '' && trim($segments[1]) !== '';
|
||||
return count($segments) >= 3 && trim($segments[0]) !== '' && trim($segments[1]) !== '';
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the recaller's segments.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
public function segments()
|
||||
{
|
||||
return explode('|', $this->recaller);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,8 +2,9 @@
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Contracts\Auth\Guard;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Support\Traits\Macroable;
|
||||
|
||||
class RequestGuard implements Guard
|
||||
@@ -29,12 +30,14 @@ class RequestGuard implements Guard
|
||||
*
|
||||
* @param callable $callback
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Illuminate\Contracts\Auth\UserProvider|null $provider
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(callable $callback, Request $request)
|
||||
public function __construct(callable $callback, Request $request, UserProvider $provider = null)
|
||||
{
|
||||
$this->request = $request;
|
||||
$this->callback = $callback;
|
||||
$this->provider = $provider;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -52,7 +55,7 @@ class RequestGuard implements Guard
|
||||
}
|
||||
|
||||
return $this->user = call_user_func(
|
||||
$this->callback, $this->request
|
||||
$this->callback, $this->request, $this->getProvider()
|
||||
);
|
||||
}
|
||||
|
||||
@@ -65,7 +68,7 @@ class RequestGuard implements Guard
|
||||
public function validate(array $credentials = [])
|
||||
{
|
||||
return ! is_null((new static(
|
||||
$this->callback, $credentials['request']
|
||||
$this->callback, $credentials['request'], $this->getProvider()
|
||||
))->user());
|
||||
}
|
||||
|
||||
|
||||
@@ -2,25 +2,37 @@
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use RuntimeException;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Http\Response;
|
||||
use Illuminate\Support\Traits\Macroable;
|
||||
use Illuminate\Contracts\Session\Session;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
use Illuminate\Contracts\Auth\StatefulGuard;
|
||||
use Symfony\Component\HttpFoundation\Request;
|
||||
use Illuminate\Contracts\Auth\SupportsBasicAuth;
|
||||
use Illuminate\Contracts\Cookie\QueueingFactory as CookieJar;
|
||||
use Illuminate\Auth\Events\Attempting;
|
||||
use Illuminate\Auth\Events\Authenticated;
|
||||
use Illuminate\Auth\Events\CurrentDeviceLogout;
|
||||
use Illuminate\Auth\Events\Failed;
|
||||
use Illuminate\Auth\Events\Login;
|
||||
use Illuminate\Auth\Events\Logout;
|
||||
use Illuminate\Auth\Events\OtherDeviceLogout;
|
||||
use Illuminate\Auth\Events\Validated;
|
||||
use Illuminate\Contracts\Auth\Authenticatable as AuthenticatableContract;
|
||||
use Illuminate\Contracts\Auth\StatefulGuard;
|
||||
use Illuminate\Contracts\Auth\SupportsBasicAuth;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Contracts\Cookie\QueueingFactory as CookieJar;
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
use Illuminate\Contracts\Session\Session;
|
||||
use Illuminate\Support\Arr;
|
||||
use Illuminate\Support\Facades\Hash;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Support\Timebox;
|
||||
use Illuminate\Support\Traits\Macroable;
|
||||
use InvalidArgumentException;
|
||||
use RuntimeException;
|
||||
use Symfony\Component\HttpFoundation\Request;
|
||||
use Symfony\Component\HttpKernel\Exception\UnauthorizedHttpException;
|
||||
|
||||
class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
{
|
||||
use GuardHelpers, Macroable;
|
||||
|
||||
/**
|
||||
* The name of the Guard. Typically "session".
|
||||
* The name of the guard. Typically "web".
|
||||
*
|
||||
* Corresponds to guard name in authentication configuration.
|
||||
*
|
||||
@@ -42,6 +54,13 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected $viaRemember = false;
|
||||
|
||||
/**
|
||||
* The number of minutes that the "remember me" cookie should be valid for.
|
||||
*
|
||||
* @var int
|
||||
*/
|
||||
protected $rememberDuration = 576000;
|
||||
|
||||
/**
|
||||
* The session used by the guard.
|
||||
*
|
||||
@@ -70,6 +89,13 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected $events;
|
||||
|
||||
/**
|
||||
* The timebox instance.
|
||||
*
|
||||
* @var \Illuminate\Support\Timebox
|
||||
*/
|
||||
protected $timebox;
|
||||
|
||||
/**
|
||||
* Indicates if the logout method has been called.
|
||||
*
|
||||
@@ -90,18 +116,21 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
* @param string $name
|
||||
* @param \Illuminate\Contracts\Auth\UserProvider $provider
|
||||
* @param \Illuminate\Contracts\Session\Session $session
|
||||
* @param \Symfony\Component\HttpFoundation\Request $request
|
||||
* @param \Symfony\Component\HttpFoundation\Request|null $request
|
||||
* @param \Illuminate\Support\Timebox|null $timebox
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($name,
|
||||
UserProvider $provider,
|
||||
Session $session,
|
||||
Request $request = null)
|
||||
Request $request = null,
|
||||
Timebox $timebox = null)
|
||||
{
|
||||
$this->name = $name;
|
||||
$this->session = $session;
|
||||
$this->request = $request;
|
||||
$this->provider = $provider;
|
||||
$this->timebox = $timebox ?: new Timebox;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -127,30 +156,24 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
// First we will try to load the user using the identifier in the session if
|
||||
// one exists. Otherwise we will check for a "remember me" cookie in this
|
||||
// request, and if one exists, attempt to retrieve the user using that.
|
||||
$user = null;
|
||||
|
||||
if (! is_null($id)) {
|
||||
if ($user = $this->provider->retrieveById($id)) {
|
||||
$this->fireAuthenticatedEvent($user);
|
||||
}
|
||||
if (! is_null($id) && $this->user = $this->provider->retrieveById($id)) {
|
||||
$this->fireAuthenticatedEvent($this->user);
|
||||
}
|
||||
|
||||
// If the user is null, but we decrypt a "recaller" cookie we can attempt to
|
||||
// pull the user data on that cookie which serves as a remember cookie on
|
||||
// the application. Once we have a user we can return it to the caller.
|
||||
$recaller = $this->recaller();
|
||||
if (is_null($this->user) && ! is_null($recaller = $this->recaller())) {
|
||||
$this->user = $this->userFromRecaller($recaller);
|
||||
|
||||
if (is_null($user) && ! is_null($recaller)) {
|
||||
$user = $this->userFromRecaller($recaller);
|
||||
if ($this->user) {
|
||||
$this->updateSession($this->user->getAuthIdentifier());
|
||||
|
||||
if ($user) {
|
||||
$this->updateSession($user->getAuthIdentifier());
|
||||
|
||||
$this->fireLoginEvent($user, true);
|
||||
$this->fireLoginEvent($this->user, true);
|
||||
}
|
||||
}
|
||||
|
||||
return $this->user = $user;
|
||||
return $this->user;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -196,7 +219,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
/**
|
||||
* Get the ID for the currently authenticated user.
|
||||
*
|
||||
* @return int|null
|
||||
* @return int|string|null
|
||||
*/
|
||||
public function id()
|
||||
{
|
||||
@@ -264,6 +287,8 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
* @param string $field
|
||||
* @param array $extraConditions
|
||||
* @return \Symfony\Component\HttpFoundation\Response|null
|
||||
*
|
||||
* @throws \Symfony\Component\HttpKernel\Exception\UnauthorizedHttpException
|
||||
*/
|
||||
public function basic($field = 'email', $extraConditions = [])
|
||||
{
|
||||
@@ -287,6 +312,8 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
* @param string $field
|
||||
* @param array $extraConditions
|
||||
* @return \Symfony\Component\HttpFoundation\Response|null
|
||||
*
|
||||
* @throws \Symfony\Component\HttpKernel\Exception\UnauthorizedHttpException
|
||||
*/
|
||||
public function onceBasic($field = 'email', $extraConditions = [])
|
||||
{
|
||||
@@ -317,7 +344,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the credential array for a HTTP Basic request.
|
||||
* Get the credential array for an HTTP Basic request.
|
||||
*
|
||||
* @param \Symfony\Component\HttpFoundation\Request $request
|
||||
* @param string $field
|
||||
@@ -331,18 +358,20 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
/**
|
||||
* Get the response for basic authentication.
|
||||
*
|
||||
* @return \Symfony\Component\HttpFoundation\Response
|
||||
* @return void
|
||||
*
|
||||
* @throws \Symfony\Component\HttpKernel\Exception\UnauthorizedHttpException
|
||||
*/
|
||||
protected function failedBasicResponse()
|
||||
{
|
||||
return new Response('Invalid credentials.', 401, ['WWW-Authenticate' => 'Basic']);
|
||||
throw new UnauthorizedHttpException('Basic', 'Invalid credentials.');
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to authenticate a user using the given credentials.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @param bool $remember
|
||||
* @param bool $remember
|
||||
* @return bool
|
||||
*/
|
||||
public function attempt(array $credentials = [], $remember = false)
|
||||
@@ -368,6 +397,34 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to authenticate a user with credentials and additional callbacks.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @param array|callable|null $callbacks
|
||||
* @param bool $remember
|
||||
* @return bool
|
||||
*/
|
||||
public function attemptWhen(array $credentials = [], $callbacks = null, $remember = false)
|
||||
{
|
||||
$this->fireAttemptEvent($credentials, $remember);
|
||||
|
||||
$this->lastAttempted = $user = $this->provider->retrieveByCredentials($credentials);
|
||||
|
||||
// This method does the exact same thing as attempt, but also executes callbacks after
|
||||
// the user is retrieved and validated. If one of the callbacks returns falsy we do
|
||||
// not login the user. Instead, we will fail the specific authentication attempt.
|
||||
if ($this->hasValidCredentials($user, $credentials) && $this->shouldLogin($callbacks, $user)) {
|
||||
$this->login($user, $remember);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
$this->fireFailedEvent($user, $credentials);
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the user matches the credentials.
|
||||
*
|
||||
@@ -377,14 +434,42 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected function hasValidCredentials($user, $credentials)
|
||||
{
|
||||
return ! is_null($user) && $this->provider->validateCredentials($user, $credentials);
|
||||
return $this->timebox->call(function ($timebox) use ($user, $credentials) {
|
||||
$validated = ! is_null($user) && $this->provider->validateCredentials($user, $credentials);
|
||||
|
||||
if ($validated) {
|
||||
$timebox->returnEarly();
|
||||
|
||||
$this->fireValidatedEvent($user);
|
||||
}
|
||||
|
||||
return $validated;
|
||||
}, 200 * 1000);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the user should login by executing the given callbacks.
|
||||
*
|
||||
* @param array|callable|null $callbacks
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return bool
|
||||
*/
|
||||
protected function shouldLogin($callbacks, AuthenticatableContract $user)
|
||||
{
|
||||
foreach (Arr::wrap($callbacks) as $callback) {
|
||||
if (! $callback($user, $this)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Log the given user ID into the application.
|
||||
*
|
||||
* @param mixed $id
|
||||
* @param bool $remember
|
||||
* @param bool $remember
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable|false
|
||||
*/
|
||||
public function loginUsingId($id, $remember = false)
|
||||
@@ -461,7 +546,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
protected function queueRecallerCookie(AuthenticatableContract $user)
|
||||
{
|
||||
$this->getCookieJar()->queue($this->createRecaller(
|
||||
$user->getAuthIdentifier().'|'.$user->getRememberToken()
|
||||
$user->getAuthIdentifier().'|'.$user->getRememberToken().'|'.$user->getAuthPassword()
|
||||
));
|
||||
}
|
||||
|
||||
@@ -473,7 +558,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected function createRecaller($value)
|
||||
{
|
||||
return $this->getCookieJar()->forever($this->getRecallerName(), $value);
|
||||
return $this->getCookieJar()->make($this->getRecallerName(), $value, $this->getRememberDuration());
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -485,17 +570,45 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
{
|
||||
$user = $this->user();
|
||||
|
||||
// If we have an event dispatcher instance, we can fire off the logout event
|
||||
// so any further processing can be done. This allows the developer to be
|
||||
// listening for anytime a user signs out of this application manually.
|
||||
$this->clearUserDataFromStorage();
|
||||
|
||||
if (! is_null($this->user)) {
|
||||
if (! is_null($this->user) && ! empty($user->getRememberToken())) {
|
||||
$this->cycleRememberToken($user);
|
||||
}
|
||||
|
||||
// If we have an event dispatcher instance, we can fire off the logout event
|
||||
// so any further processing can be done. This allows the developer to be
|
||||
// listening for anytime a user signs out of this application manually.
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Logout($user));
|
||||
$this->events->dispatch(new Logout($this->name, $user));
|
||||
}
|
||||
|
||||
// Once we have fired the logout event we will clear the users out of memory
|
||||
// so they are no longer available as the user is no longer considered as
|
||||
// being signed into this application and should not be available here.
|
||||
$this->user = null;
|
||||
|
||||
$this->loggedOut = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Log the user out of the application on their current device only.
|
||||
*
|
||||
* This method does not cycle the "remember" token.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function logoutCurrentDevice()
|
||||
{
|
||||
$user = $this->user();
|
||||
|
||||
$this->clearUserDataFromStorage();
|
||||
|
||||
// If we have an event dispatcher instance, we can fire off the logout event
|
||||
// so any further processing can be done. This allows the developer to be
|
||||
// listening for anytime a user signs out of this application manually.
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new CurrentDeviceLogout($this->name, $user));
|
||||
}
|
||||
|
||||
// Once we have fired the logout event we will clear the users out of memory
|
||||
@@ -515,9 +628,12 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
{
|
||||
$this->session->remove($this->getName());
|
||||
|
||||
$this->getCookieJar()->unqueue($this->getRecallerName());
|
||||
|
||||
if (! is_null($this->recaller())) {
|
||||
$this->getCookieJar()->queue($this->getCookieJar()
|
||||
->forget($this->getRecallerName()));
|
||||
$this->getCookieJar()->queue(
|
||||
$this->getCookieJar()->forget($this->getRecallerName())
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -534,6 +650,55 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
$this->provider->updateRememberToken($user, $token);
|
||||
}
|
||||
|
||||
/**
|
||||
* Invalidate other sessions for the current user.
|
||||
*
|
||||
* The application must be using the AuthenticateSession middleware.
|
||||
*
|
||||
* @param string $password
|
||||
* @param string $attribute
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable|null
|
||||
*
|
||||
* @throws \Illuminate\Auth\AuthenticationException
|
||||
*/
|
||||
public function logoutOtherDevices($password, $attribute = 'password')
|
||||
{
|
||||
if (! $this->user()) {
|
||||
return;
|
||||
}
|
||||
|
||||
$result = $this->rehashUserPassword($password, $attribute);
|
||||
|
||||
if ($this->recaller() ||
|
||||
$this->getCookieJar()->hasQueued($this->getRecallerName())) {
|
||||
$this->queueRecallerCookie($this->user());
|
||||
}
|
||||
|
||||
$this->fireOtherDeviceLogoutEvent($this->user());
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Rehash the current user's password.
|
||||
*
|
||||
* @param string $password
|
||||
* @param string $attribute
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable|null
|
||||
*
|
||||
* @throws \InvalidArgumentException
|
||||
*/
|
||||
protected function rehashUserPassword($password, $attribute)
|
||||
{
|
||||
if (! Hash::check($password, $this->user()->{$attribute})) {
|
||||
throw new InvalidArgumentException('The given password does not match the current password.');
|
||||
}
|
||||
|
||||
return tap($this->user()->forceFill([
|
||||
$attribute => Hash::make($password),
|
||||
]))->save();
|
||||
}
|
||||
|
||||
/**
|
||||
* Register an authentication attempt event listener.
|
||||
*
|
||||
@@ -542,9 +707,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
public function attempting($callback)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->listen(Events\Attempting::class, $callback);
|
||||
}
|
||||
$this->events?->listen(Events\Attempting::class, $callback);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -556,11 +719,18 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected function fireAttemptEvent(array $credentials, $remember = false)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Attempting(
|
||||
$credentials, $remember
|
||||
));
|
||||
}
|
||||
$this->events?->dispatch(new Attempting($this->name, $credentials, $remember));
|
||||
}
|
||||
|
||||
/**
|
||||
* Fires the validated event if the dispatcher is set.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
protected function fireValidatedEvent($user)
|
||||
{
|
||||
$this->events?->dispatch(new Validated($this->name, $user));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -572,9 +742,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected function fireLoginEvent($user, $remember = false)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Login($user, $remember));
|
||||
}
|
||||
$this->events?->dispatch(new Login($this->name, $user, $remember));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -585,9 +753,18 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected function fireAuthenticatedEvent($user)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Authenticated($user));
|
||||
}
|
||||
$this->events?->dispatch(new Authenticated($this->name, $user));
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire the other device logout event if the dispatcher is set.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
protected function fireOtherDeviceLogoutEvent($user)
|
||||
{
|
||||
$this->events?->dispatch(new OtherDeviceLogout($this->name, $user));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -599,9 +776,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected function fireFailedEvent($user, array $credentials)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Failed($user, $credentials));
|
||||
}
|
||||
$this->events?->dispatch(new Failed($this->name, $user, $credentials));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -644,6 +819,29 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
return $this->viaRemember;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the number of minutes the remember me cookie should be valid for.
|
||||
*
|
||||
* @return int
|
||||
*/
|
||||
protected function getRememberDuration()
|
||||
{
|
||||
return $this->rememberDuration;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the number of minutes the remember me cookie should be valid for.
|
||||
*
|
||||
* @param int $minutes
|
||||
* @return $this
|
||||
*/
|
||||
public function setRememberDuration($minutes)
|
||||
{
|
||||
$this->rememberDuration = $minutes;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the cookie creator instance used by the guard.
|
||||
*
|
||||
@@ -695,34 +893,13 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
/**
|
||||
* Get the session store used by the guard.
|
||||
*
|
||||
* @return \Illuminate\Session\Store
|
||||
* @return \Illuminate\Contracts\Session\Session
|
||||
*/
|
||||
public function getSession()
|
||||
{
|
||||
return $this->session;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the user provider used by the guard.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Auth\UserProvider
|
||||
*/
|
||||
public function getProvider()
|
||||
{
|
||||
return $this->provider;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the user provider used by the guard.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\UserProvider $provider
|
||||
* @return void
|
||||
*/
|
||||
public function setProvider(UserProvider $provider)
|
||||
{
|
||||
$this->provider = $provider;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the currently cached user.
|
||||
*
|
||||
@@ -772,4 +949,14 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the timebox instance used by the guard.
|
||||
*
|
||||
* @return \Illuminate\Support\Timebox
|
||||
*/
|
||||
public function getTimebox()
|
||||
{
|
||||
return $this->timebox;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,9 +2,9 @@
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Contracts\Auth\Guard;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class TokenGuard implements Guard
|
||||
{
|
||||
@@ -31,19 +31,35 @@ class TokenGuard implements Guard
|
||||
*/
|
||||
protected $storageKey;
|
||||
|
||||
/**
|
||||
* Indicates if the API token is hashed in storage.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
protected $hash = false;
|
||||
|
||||
/**
|
||||
* Create a new authentication guard.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\UserProvider $provider
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param string $inputKey
|
||||
* @param string $storageKey
|
||||
* @param bool $hash
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(UserProvider $provider, Request $request)
|
||||
public function __construct(
|
||||
UserProvider $provider,
|
||||
Request $request,
|
||||
$inputKey = 'api_token',
|
||||
$storageKey = 'api_token',
|
||||
$hash = false)
|
||||
{
|
||||
$this->hash = $hash;
|
||||
$this->request = $request;
|
||||
$this->provider = $provider;
|
||||
$this->inputKey = 'api_token';
|
||||
$this->storageKey = 'api_token';
|
||||
$this->inputKey = $inputKey;
|
||||
$this->storageKey = $storageKey;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -65,9 +81,9 @@ class TokenGuard implements Guard
|
||||
$token = $this->getTokenForRequest();
|
||||
|
||||
if (! empty($token)) {
|
||||
$user = $this->provider->retrieveByCredentials(
|
||||
[$this->storageKey => $token]
|
||||
);
|
||||
$user = $this->provider->retrieveByCredentials([
|
||||
$this->storageKey => $this->hash ? hash('sha256', $token) : $token,
|
||||
]);
|
||||
}
|
||||
|
||||
return $this->user = $user;
|
||||
|
||||
@@ -14,12 +14,13 @@
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=5.6.4",
|
||||
"illuminate/contracts": "5.4.*",
|
||||
"illuminate/http": "5.4.*",
|
||||
"illuminate/queue": "5.4.*",
|
||||
"illuminate/support": "5.4.*",
|
||||
"nesbot/carbon": "~1.20"
|
||||
"php": "^8.0.2",
|
||||
"illuminate/collections": "^9.0",
|
||||
"illuminate/contracts": "^9.0",
|
||||
"illuminate/http": "^9.0",
|
||||
"illuminate/macroable": "^9.0",
|
||||
"illuminate/queue": "^9.0",
|
||||
"illuminate/support": "^9.0"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
@@ -28,13 +29,13 @@
|
||||
},
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "5.4-dev"
|
||||
"dev-master": "9.x-dev"
|
||||
}
|
||||
},
|
||||
"suggest": {
|
||||
"illuminate/console": "Required to use the auth:clear-resets command (5.4.*).",
|
||||
"illuminate/queue": "Required to fire login / logout events (5.4.*).",
|
||||
"illuminate/session": "Required to use the session based guard (5.4.*)."
|
||||
"illuminate/console": "Required to use the auth:clear-resets command (^9.0).",
|
||||
"illuminate/queue": "Required to fire login / logout events (^9.0).",
|
||||
"illuminate/session": "Required to use the session based guard (^9.0)."
|
||||
},
|
||||
"config": {
|
||||
"sort-packages": true
|
||||
|
||||
Reference in New Issue
Block a user