Laravel version update
Laravel version update
This commit is contained in:
@@ -2,6 +2,7 @@
|
||||
|
||||
namespace Illuminate\Auth\Access;
|
||||
|
||||
use Illuminate\Support\Arr;
|
||||
use Illuminate\Support\Str;
|
||||
use InvalidArgumentException;
|
||||
use Illuminate\Contracts\Container\Container;
|
||||
@@ -64,7 +65,8 @@ class Gate implements GateContract
|
||||
* @param array $afterCallbacks
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Container $container, callable $userResolver, array $abilities = [], array $policies = [], array $beforeCallbacks = [], array $afterCallbacks = [])
|
||||
public function __construct(Container $container, callable $userResolver, array $abilities = [],
|
||||
array $policies = [], array $beforeCallbacks = [], array $afterCallbacks = [])
|
||||
{
|
||||
$this->policies = $policies;
|
||||
$this->container = $container;
|
||||
@@ -77,12 +79,20 @@ class Gate implements GateContract
|
||||
/**
|
||||
* 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;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -99,7 +109,7 @@ class Gate implements GateContract
|
||||
if (is_callable($callback)) {
|
||||
$this->abilities[$ability] = $callback;
|
||||
} elseif (is_string($callback) && Str::contains($callback, '@')) {
|
||||
$this->abilities[$ability] = $this->buildAbilityCallback($callback);
|
||||
$this->abilities[$ability] = $this->buildAbilityCallback($ability, $callback);
|
||||
} else {
|
||||
throw new InvalidArgumentException("Callback must be a callable or a 'Class@method' string.");
|
||||
}
|
||||
@@ -107,18 +117,57 @@ class Gate implements GateContract
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Define abilities for a resource.
|
||||
*
|
||||
* @param string $name
|
||||
* @param string $class
|
||||
* @param array $abilities
|
||||
* @return $this
|
||||
*/
|
||||
public function resource($name, $class, array $abilities = null)
|
||||
{
|
||||
$abilities = $abilities ?: [
|
||||
'view' => 'view',
|
||||
'create' => 'create',
|
||||
'update' => 'update',
|
||||
'delete' => 'delete',
|
||||
];
|
||||
|
||||
foreach ($abilities as $ability => $method) {
|
||||
$this->define($name.'.'.$ability, $class.'@'.$method);
|
||||
}
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* 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) = explode('@', $callback);
|
||||
return function () use ($ability, $callback) {
|
||||
list($class, $method) = Str::parseCallback($callback);
|
||||
|
||||
return call_user_func_array([$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 $policy->{$method}(...func_get_args());
|
||||
};
|
||||
}
|
||||
|
||||
@@ -187,21 +236,35 @@ 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 {
|
||||
$result = $this->raw($ability, $arguments);
|
||||
} catch (AuthorizationException $e) {
|
||||
return false;
|
||||
}
|
||||
return collect($abilities)->every(function ($ability) use ($arguments) {
|
||||
try {
|
||||
return (bool) $this->raw($ability, $arguments);
|
||||
} catch (AuthorizationException $e) {
|
||||
return false;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return (bool) $result;
|
||||
/**
|
||||
* 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(function ($ability) use ($arguments) {
|
||||
return $this->check($ability, $arguments);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -225,7 +288,7 @@ class Gate implements GateContract
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the raw result for the given ability for the current user.
|
||||
* Get the raw result from the authorization callback.
|
||||
*
|
||||
* @param string $ability
|
||||
* @param array|mixed $arguments
|
||||
@@ -237,12 +300,22 @@ class Gate implements GateContract
|
||||
return false;
|
||||
}
|
||||
|
||||
$arguments = is_array($arguments) ? $arguments : [$arguments];
|
||||
$arguments = Arr::wrap($arguments);
|
||||
|
||||
if (is_null($result = $this->callBeforeCallbacks($user, $ability, $arguments))) {
|
||||
// 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
|
||||
// to let the developers override all checks for some authorization cases.
|
||||
$result = $this->callBeforeCallbacks(
|
||||
$user, $ability, $arguments
|
||||
);
|
||||
|
||||
if (is_null($result)) {
|
||||
$result = $this->callAuthCallback($user, $ability, $arguments);
|
||||
}
|
||||
|
||||
// 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(
|
||||
$user, $ability, $arguments, $result
|
||||
);
|
||||
@@ -260,13 +333,9 @@ class Gate implements GateContract
|
||||
*/
|
||||
protected function callAuthCallback($user, $ability, array $arguments)
|
||||
{
|
||||
$callback = $this->resolveAuthCallback(
|
||||
$user, $ability, $arguments
|
||||
);
|
||||
$callback = $this->resolveAuthCallback($user, $ability, $arguments);
|
||||
|
||||
return call_user_func_array(
|
||||
$callback, array_merge([$user], $arguments)
|
||||
);
|
||||
return $callback($user, ...$arguments);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -282,7 +351,7 @@ class Gate implements GateContract
|
||||
$arguments = array_merge([$user, $ability], [$arguments]);
|
||||
|
||||
foreach ($this->beforeCallbacks as $before) {
|
||||
if (! is_null($result = call_user_func_array($before, $arguments))) {
|
||||
if (! is_null($result = $before(...$arguments))) {
|
||||
return $result;
|
||||
}
|
||||
}
|
||||
@@ -302,7 +371,7 @@ class Gate implements GateContract
|
||||
$arguments = array_merge([$user, $ability, $result], [$arguments]);
|
||||
|
||||
foreach ($this->afterCallbacks as $after) {
|
||||
call_user_func_array($after, $arguments);
|
||||
$after(...$arguments);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -316,78 +385,18 @@ class Gate implements GateContract
|
||||
*/
|
||||
protected function resolveAuthCallback($user, $ability, array $arguments)
|
||||
{
|
||||
if ($this->firstArgumentCorrespondsToPolicy($arguments)) {
|
||||
return $this->resolvePolicyCallback($user, $ability, $arguments);
|
||||
} elseif (isset($this->abilities[$ability])) {
|
||||
if (isset($arguments[0]) &&
|
||||
! is_null($policy = $this->getPolicyFor($arguments[0])) &&
|
||||
$callback = $this->resolvePolicyCallback($user, $ability, $arguments, $policy)) {
|
||||
return $callback;
|
||||
}
|
||||
|
||||
if (isset($this->abilities[$ability])) {
|
||||
return $this->abilities[$ability];
|
||||
} else {
|
||||
return function () {
|
||||
return false;
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the first argument in the array corresponds to a policy.
|
||||
*
|
||||
* @param array $arguments
|
||||
* @return bool
|
||||
*/
|
||||
protected function firstArgumentCorrespondsToPolicy(array $arguments)
|
||||
{
|
||||
if (! isset($arguments[0])) {
|
||||
return function () {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (is_object($arguments[0])) {
|
||||
return isset($this->policies[get_class($arguments[0])]);
|
||||
}
|
||||
|
||||
return is_string($arguments[0]) && isset($this->policies[$arguments[0]]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve the callback for a policy check.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @return callable
|
||||
*/
|
||||
protected function resolvePolicyCallback($user, $ability, array $arguments)
|
||||
{
|
||||
return function () use ($user, $ability, $arguments) {
|
||||
$instance = $this->getPolicyFor($arguments[0]);
|
||||
|
||||
if (method_exists($instance, 'before')) {
|
||||
// We will prepend the user and ability onto the arguments so that the before
|
||||
// callback can determine which ability is being called. Then we will call
|
||||
// into the policy before methods with the arguments and get the result.
|
||||
$beforeArguments = array_merge([$user, $ability], $arguments);
|
||||
|
||||
$result = call_user_func_array(
|
||||
[$instance, 'before'], $beforeArguments
|
||||
);
|
||||
|
||||
// If we received a non-null result from the before method, we will return it
|
||||
// as the result of a check. This allows developers to override the checks
|
||||
// in the policy and return a result for all rules defined in the class.
|
||||
if (! is_null($result)) {
|
||||
return $result;
|
||||
}
|
||||
}
|
||||
|
||||
if (strpos($ability, '-') !== false) {
|
||||
$ability = Str::camel($ability);
|
||||
}
|
||||
|
||||
if (! is_callable([$instance, $ability])) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return call_user_func_array(
|
||||
[$instance, $ability], array_merge([$user], $arguments)
|
||||
);
|
||||
};
|
||||
}
|
||||
|
||||
@@ -396,8 +405,6 @@ class Gate implements GateContract
|
||||
*
|
||||
* @param object|string $class
|
||||
* @return mixed
|
||||
*
|
||||
* @throws \InvalidArgumentException
|
||||
*/
|
||||
public function getPolicyFor($class)
|
||||
{
|
||||
@@ -405,11 +412,19 @@ class Gate implements GateContract
|
||||
$class = get_class($class);
|
||||
}
|
||||
|
||||
if (! isset($this->policies[$class])) {
|
||||
throw new InvalidArgumentException("Policy not defined for [{$class}].");
|
||||
if (! is_string($class)) {
|
||||
return;
|
||||
}
|
||||
|
||||
return $this->resolvePolicy($this->policies[$class]);
|
||||
if (isset($this->policies[$class])) {
|
||||
return $this->resolvePolicy($this->policies[$class]);
|
||||
}
|
||||
|
||||
foreach ($this->policies as $expected => $policy) {
|
||||
if (is_subclass_of($class, $expected)) {
|
||||
return $this->resolvePolicy($policy);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -423,6 +438,78 @@ class Gate implements GateContract
|
||||
return $this->container->make($class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve the callback for a policy check.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @param mixed $policy
|
||||
* @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
|
||||
// mapped to policy objects in the user's configurations or on this class.
|
||||
$result = $this->callPolicyBefore(
|
||||
$policy, $user, $ability, $arguments
|
||||
);
|
||||
|
||||
// When we receive a non-null result from this before method, we will return it
|
||||
// as the "final" results. This will allow developers to override the checks
|
||||
// in this policy to return the result for all rules defined in the class.
|
||||
if (! is_null($result)) {
|
||||
return $result;
|
||||
}
|
||||
|
||||
$ability = $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;
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Call the "before" method on the given policy, if applicable.
|
||||
*
|
||||
* @param mixed $policy
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param string $ability
|
||||
* @param array $arguments
|
||||
* @return mixed
|
||||
*/
|
||||
protected function callPolicyBefore($policy, $user, $ability, $arguments)
|
||||
{
|
||||
if (method_exists($policy, 'before')) {
|
||||
return $policy->before($user, $ability, ...$arguments);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Format the policy ability into a method name.
|
||||
*
|
||||
* @param string $ability
|
||||
* @return string
|
||||
*/
|
||||
protected function formatAbilityToMethod($ability)
|
||||
{
|
||||
return strpos($ability, '-') !== false ? Str::camel($ability) : $ability;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a gate instance for the given user.
|
||||
*
|
||||
@@ -450,4 +537,24 @@ class Gate implements GateContract
|
||||
{
|
||||
return call_user_func($this->userResolver);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all of the defined abilities.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
public function abilities()
|
||||
{
|
||||
return $this->abilities;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all of the defined policies.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
public function policies()
|
||||
{
|
||||
return $this->policies;
|
||||
}
|
||||
}
|
||||
|
@@ -15,6 +15,7 @@ class Response
|
||||
* Create a new response.
|
||||
*
|
||||
* @param string|null $message
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($message = null)
|
||||
{
|
||||
|
@@ -65,9 +65,7 @@ class AuthManager implements FactoryContract
|
||||
{
|
||||
$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);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -88,15 +86,15 @@ class AuthManager implements FactoryContract
|
||||
|
||||
if (isset($this->customCreators[$config['driver']])) {
|
||||
return $this->callCustomCreator($name, $config);
|
||||
} else {
|
||||
$driverMethod = 'create'.ucfirst($config['driver']).'Driver';
|
||||
|
||||
if (method_exists($this, $driverMethod)) {
|
||||
return $this->{$driverMethod}($name, $config);
|
||||
} else {
|
||||
throw new InvalidArgumentException("Auth guard driver [{$name}] is not defined.");
|
||||
}
|
||||
}
|
||||
|
||||
$driverMethod = 'create'.ucfirst($config['driver']).'Driver';
|
||||
|
||||
if (method_exists($this, $driverMethod)) {
|
||||
return $this->{$driverMethod}($name, $config);
|
||||
}
|
||||
|
||||
throw new InvalidArgumentException("Auth guard driver [{$name}] is not defined.");
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -120,7 +118,7 @@ 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']);
|
||||
|
||||
@@ -155,7 +153,7 @@ 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->createUserProvider($config['provider'] ?? null),
|
||||
$this->app['request']
|
||||
);
|
||||
|
||||
@@ -193,6 +191,8 @@ class AuthManager implements FactoryContract
|
||||
*/
|
||||
public function shouldUse($name)
|
||||
{
|
||||
$name = $name ?: $this->getDefaultDriver();
|
||||
|
||||
$this->setDefaultDriver($name);
|
||||
|
||||
$this->userResolver = function ($name = null) {
|
||||
@@ -221,7 +221,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');
|
||||
|
||||
@@ -289,6 +289,6 @@ class AuthManager implements FactoryContract
|
||||
*/
|
||||
public function __call($method, $parameters)
|
||||
{
|
||||
return call_user_func_array([$this->guard(), $method], $parameters);
|
||||
return $this->guard()->{$method}(...$parameters);
|
||||
}
|
||||
}
|
||||
|
@@ -4,6 +4,13 @@ namespace Illuminate\Auth;
|
||||
|
||||
trait Authenticatable
|
||||
{
|
||||
/**
|
||||
* The column name of the "remember me" token.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $rememberTokenName = 'remember_token';
|
||||
|
||||
/**
|
||||
* Get the name of the unique identifier for the user.
|
||||
*
|
||||
@@ -21,7 +28,7 @@ trait Authenticatable
|
||||
*/
|
||||
public function getAuthIdentifier()
|
||||
{
|
||||
return $this->getKey();
|
||||
return $this->{$this->getAuthIdentifierName()};
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -37,11 +44,13 @@ trait Authenticatable
|
||||
/**
|
||||
* Get the token value for the "remember me" session.
|
||||
*
|
||||
* @return string
|
||||
* @return string|null
|
||||
*/
|
||||
public function getRememberToken()
|
||||
{
|
||||
return $this->{$this->getRememberTokenName()};
|
||||
if (! empty($this->getRememberTokenName())) {
|
||||
return (string) $this->{$this->getRememberTokenName()};
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -52,7 +61,9 @@ trait Authenticatable
|
||||
*/
|
||||
public function setRememberToken($value)
|
||||
{
|
||||
$this->{$this->getRememberTokenName()} = $value;
|
||||
if (! empty($this->getRememberTokenName())) {
|
||||
$this->{$this->getRememberTokenName()} = $value;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -62,6 +73,6 @@ trait Authenticatable
|
||||
*/
|
||||
public function getRememberTokenName()
|
||||
{
|
||||
return 'remember_token';
|
||||
return $this->rememberTokenName;
|
||||
}
|
||||
}
|
||||
|
@@ -7,31 +7,33 @@ use Exception;
|
||||
class AuthenticationException extends Exception
|
||||
{
|
||||
/**
|
||||
* The guard instance.
|
||||
* All of the guards that were checked.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Guard
|
||||
* @var array
|
||||
*/
|
||||
protected $guard;
|
||||
protected $guards;
|
||||
|
||||
/**
|
||||
* Create a new authentication exception.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Guard|null $guard
|
||||
* @param string $message
|
||||
* @param array $guards
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($guard = null)
|
||||
public function __construct($message = 'Unauthenticated.', array $guards = [])
|
||||
{
|
||||
$this->guard = $guard;
|
||||
parent::__construct($message);
|
||||
|
||||
parent::__construct('Unauthenticated.');
|
||||
$this->guards = $guards;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the guard instance.
|
||||
* Get the guards that were checked.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Auth\Guard|null
|
||||
* @return array
|
||||
*/
|
||||
public function guard()
|
||||
public function guards()
|
||||
{
|
||||
return $this->guard;
|
||||
return $this->guards;
|
||||
}
|
||||
}
|
||||
|
@@ -3,18 +3,20 @@
|
||||
namespace Illuminate\Auth\Console;
|
||||
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Console\AppNamespaceDetectorTrait;
|
||||
use Illuminate\Console\DetectsApplicationNamespace;
|
||||
|
||||
class MakeAuthCommand extends Command
|
||||
class AuthMakeCommand extends Command
|
||||
{
|
||||
use AppNamespaceDetectorTrait;
|
||||
use DetectsApplicationNamespace;
|
||||
|
||||
/**
|
||||
* The name and signature of the console command.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $signature = 'make:auth {--views : Only scaffold the authentication views}';
|
||||
protected $signature = 'make:auth
|
||||
{--views : Only scaffold the authentication views}
|
||||
{--force : Overwrite existing views by default}';
|
||||
|
||||
/**
|
||||
* The console command description.
|
||||
@@ -33,10 +35,8 @@ class MakeAuthCommand extends Command
|
||||
'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',
|
||||
'auth/emails/password.stub' => 'auth/emails/password.blade.php',
|
||||
'layouts/app.stub' => 'layouts/app.blade.php',
|
||||
'home.stub' => 'home.blade.php',
|
||||
'welcome.stub' => 'welcome.blade.php',
|
||||
];
|
||||
|
||||
/**
|
||||
@@ -44,30 +44,26 @@ class MakeAuthCommand extends Command
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function fire()
|
||||
public function handle()
|
||||
{
|
||||
$this->createDirectories();
|
||||
|
||||
$this->exportViews();
|
||||
|
||||
if (! $this->option('views')) {
|
||||
$this->info('Installed HomeController.');
|
||||
|
||||
file_put_contents(
|
||||
app_path('Http/Controllers/HomeController.php'),
|
||||
$this->compileControllerStub()
|
||||
);
|
||||
|
||||
$this->info('Updated Routes File.');
|
||||
|
||||
file_put_contents(
|
||||
app_path('Http/routes.php'),
|
||||
base_path('routes/web.php'),
|
||||
file_get_contents(__DIR__.'/stubs/make/routes.stub'),
|
||||
FILE_APPEND
|
||||
);
|
||||
}
|
||||
|
||||
$this->comment('Authentication scaffolding generated successfully!');
|
||||
$this->info('Authentication scaffolding generated successfully.');
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -77,16 +73,12 @@ class MakeAuthCommand extends Command
|
||||
*/
|
||||
protected function createDirectories()
|
||||
{
|
||||
if (! is_dir(base_path('resources/views/layouts'))) {
|
||||
mkdir(base_path('resources/views/layouts'), 0755, true);
|
||||
if (! is_dir($directory = resource_path('views/layouts'))) {
|
||||
mkdir($directory, 0755, true);
|
||||
}
|
||||
|
||||
if (! is_dir(base_path('resources/views/auth/passwords'))) {
|
||||
mkdir(base_path('resources/views/auth/passwords'), 0755, true);
|
||||
}
|
||||
|
||||
if (! is_dir(base_path('resources/views/auth/emails'))) {
|
||||
mkdir(base_path('resources/views/auth/emails'), 0755, true);
|
||||
if (! is_dir($directory = resource_path('views/auth/passwords'))) {
|
||||
mkdir($directory, 0755, true);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -98,11 +90,16 @@ class MakeAuthCommand extends Command
|
||||
protected function exportViews()
|
||||
{
|
||||
foreach ($this->views as $key => $value) {
|
||||
$path = base_path('resources/views/'.$value);
|
||||
if (file_exists($view = resource_path('views/'.$value)) && ! $this->option('force')) {
|
||||
if (! $this->confirm("The [{$value}] view already exists. Do you want to replace it?")) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
$this->line('<info>Created View:</info> '.$path);
|
||||
|
||||
copy(__DIR__.'/stubs/make/views/'.$key, $path);
|
||||
copy(
|
||||
__DIR__.'/stubs/make/views/'.$key,
|
||||
$view
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@@ -25,7 +25,7 @@ class ClearResetsCommand extends Command
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function fire()
|
||||
public function handle()
|
||||
{
|
||||
$this->laravel['auth.password']->broker($this->argument('name'))->getRepository()->deleteExpired();
|
||||
|
||||
|
@@ -2,7 +2,6 @@
|
||||
|
||||
namespace {{namespace}}Http\Controllers;
|
||||
|
||||
use {{namespace}}Http\Requests;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class HomeController extends Controller
|
||||
|
@@ -1,4 +1,4 @@
|
||||
|
||||
Route::auth();
|
||||
Auth::routes();
|
||||
|
||||
Route::get('/home', 'HomeController@index');
|
||||
Route::get('/home', 'HomeController@index')->name('home');
|
||||
|
@@ -1 +0,0 @@
|
||||
Click here to reset your password: <a href="{{ $link = url('password/reset', $token).'?email='.urlencode($user->getEmailForPasswordReset()) }}"> {{ $link }} </a>
|
@@ -6,15 +6,16 @@
|
||||
<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" role="form" method="POST" action="{{ url('/login') }}">
|
||||
<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') }}">
|
||||
<input id="email" type="email" class="form-control" name="email" value="{{ old('email') }}" required autofocus>
|
||||
|
||||
@if ($errors->has('email'))
|
||||
<span class="help-block">
|
||||
@@ -28,7 +29,7 @@
|
||||
<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">
|
||||
<input id="password" type="password" class="form-control" name="password" required>
|
||||
|
||||
@if ($errors->has('password'))
|
||||
<span class="help-block">
|
||||
@@ -42,19 +43,21 @@
|
||||
<div class="col-md-6 col-md-offset-4">
|
||||
<div class="checkbox">
|
||||
<label>
|
||||
<input type="checkbox" name="remember"> Remember Me
|
||||
<input type="checkbox" name="remember" {{ old('remember') ? 'checked' : '' }}> Remember Me
|
||||
</label>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<div class="col-md-6 col-md-offset-4">
|
||||
<div class="col-md-8 col-md-offset-4">
|
||||
<button type="submit" class="btn btn-primary">
|
||||
<i class="fa fa-btn fa-sign-in"></i> Login
|
||||
Login
|
||||
</button>
|
||||
|
||||
<a class="btn btn-link" href="{{ url('/password/reset') }}">Forgot Your Password?</a>
|
||||
<a class="btn btn-link" href="{{ route('password.request') }}">
|
||||
Forgot Your Password?
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
|
@@ -1,12 +1,12 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
<!-- Main Content -->
|
||||
@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">
|
||||
@@ -14,14 +14,14 @@
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<form class="form-horizontal" role="form" method="POST" action="{{ url('/password/email') }}">
|
||||
<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') }}">
|
||||
<input id="email" type="email" class="form-control" name="email" value="{{ old('email') }}" required>
|
||||
|
||||
@if ($errors->has('email'))
|
||||
<span class="help-block">
|
||||
@@ -34,7 +34,7 @@
|
||||
<div class="form-group">
|
||||
<div class="col-md-6 col-md-offset-4">
|
||||
<button type="submit" class="btn btn-primary">
|
||||
<i class="fa fa-btn fa-envelope"></i> Send Password Reset Link
|
||||
Send Password Reset Link
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -8,7 +8,7 @@
|
||||
<div class="panel-heading">Reset Password</div>
|
||||
|
||||
<div class="panel-body">
|
||||
<form class="form-horizontal" role="form" method="POST" action="{{ url('/password/reset') }}">
|
||||
<form class="form-horizontal" method="POST" action="{{ route('password.request') }}">
|
||||
{{ csrf_field() }}
|
||||
|
||||
<input type="hidden" name="token" value="{{ $token }}">
|
||||
@@ -17,7 +17,7 @@
|
||||
<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') }}">
|
||||
<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">
|
||||
@@ -31,7 +31,7 @@
|
||||
<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">
|
||||
<input id="password" type="password" class="form-control" name="password" required>
|
||||
|
||||
@if ($errors->has('password'))
|
||||
<span class="help-block">
|
||||
@@ -44,7 +44,7 @@
|
||||
<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">
|
||||
<input id="password-confirm" type="password" class="form-control" name="password_confirmation" required>
|
||||
|
||||
@if ($errors->has('password_confirmation'))
|
||||
<span class="help-block">
|
||||
@@ -57,7 +57,7 @@
|
||||
<div class="form-group">
|
||||
<div class="col-md-6 col-md-offset-4">
|
||||
<button type="submit" class="btn btn-primary">
|
||||
<i class="fa fa-btn fa-refresh"></i> Reset Password
|
||||
Reset Password
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -6,15 +6,16 @@
|
||||
<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" role="form" method="POST" action="{{ url('/register') }}">
|
||||
<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') }}">
|
||||
<input id="name" type="text" class="form-control" name="name" value="{{ old('name') }}" required autofocus>
|
||||
|
||||
@if ($errors->has('name'))
|
||||
<span class="help-block">
|
||||
@@ -28,7 +29,7 @@
|
||||
<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') }}">
|
||||
<input id="email" type="email" class="form-control" name="email" value="{{ old('email') }}" required>
|
||||
|
||||
@if ($errors->has('email'))
|
||||
<span class="help-block">
|
||||
@@ -42,7 +43,7 @@
|
||||
<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">
|
||||
<input id="password" type="password" class="form-control" name="password" required>
|
||||
|
||||
@if ($errors->has('password'))
|
||||
<span class="help-block">
|
||||
@@ -52,24 +53,18 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group{{ $errors->has('password_confirmation') ? ' has-error' : '' }}">
|
||||
<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">
|
||||
|
||||
@if ($errors->has('password_confirmation'))
|
||||
<span class="help-block">
|
||||
<strong>{{ $errors->first('password_confirmation') }}</strong>
|
||||
</span>
|
||||
@endif
|
||||
<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">
|
||||
<i class="fa fa-btn fa-user"></i> Register
|
||||
Register
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -3,11 +3,17 @@
|
||||
@section('content')
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-10 col-md-offset-1">
|
||||
<div class="col-md-8 col-md-offset-2">
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading">Dashboard</div>
|
||||
|
||||
<div class="panel-body">
|
||||
@if (session('status'))
|
||||
<div class="alert alert-success">
|
||||
{{ session('status') }}
|
||||
</div>
|
||||
@endif
|
||||
|
||||
You are logged in!
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -1,82 +1,80 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<html lang="{{ 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">
|
||||
|
||||
<title>Laravel</title>
|
||||
<!-- CSRF Token -->
|
||||
<meta name="csrf-token" content="{{ csrf_token() }}">
|
||||
|
||||
<!-- Fonts -->
|
||||
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.5.0/css/font-awesome.min.css" integrity="sha384-XdYbMnZ/QjLh6iI4ogqCTaIjrFk87ip+ekIjefZch0Y+PvJ8CDYtEs1ipDmPorQ+" crossorigin="anonymous">
|
||||
<link rel="stylesheet" href="https://fonts.googleapis.com/css?family=Lato:100,300,400,700">
|
||||
<title>{{ config('app.name', 'Laravel') }}</title>
|
||||
|
||||
<!-- Styles -->
|
||||
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.3.6/css/bootstrap.min.css" integrity="sha384-1q8mTJOASx8j1Au+a5WDVnPi2lkFfwwEAa8hDDdjZlpLegxhjVME1fgjWPGmkzs7" crossorigin="anonymous">
|
||||
{{-- <link href="{{ elixir('css/app.css') }}" rel="stylesheet"> --}}
|
||||
|
||||
<style>
|
||||
body {
|
||||
font-family: 'Lato';
|
||||
}
|
||||
|
||||
.fa-btn {
|
||||
margin-right: 6px;
|
||||
}
|
||||
</style>
|
||||
<link href="{{ asset('css/app.css') }}" rel="stylesheet">
|
||||
</head>
|
||||
<body id="app-layout">
|
||||
<nav class="navbar navbar-default navbar-static-top">
|
||||
<div class="container">
|
||||
<div class="navbar-header">
|
||||
<body>
|
||||
<div id="app">
|
||||
<nav class="navbar navbar-default navbar-static-top">
|
||||
<div class="container">
|
||||
<div class="navbar-header">
|
||||
|
||||
<!-- 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>
|
||||
<!-- Collapsed Hamburger -->
|
||||
<button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#app-navbar-collapse" aria-expanded="false">
|
||||
<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('/') }}">
|
||||
Laravel
|
||||
</a>
|
||||
<!-- Branding Image -->
|
||||
<a class="navbar-brand" href="{{ url('/') }}">
|
||||
{{ config('app.name', 'Laravel') }}
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div class="collapse navbar-collapse" id="app-navbar-collapse">
|
||||
<!-- Left Side Of Navbar -->
|
||||
<ul class="nav navbar-nav">
|
||||
|
||||
</ul>
|
||||
|
||||
<!-- Right Side Of Navbar -->
|
||||
<ul class="nav navbar-nav navbar-right">
|
||||
<!-- Authentication Links -->
|
||||
@guest
|
||||
<li><a href="{{ route('login') }}">Login</a></li>
|
||||
<li><a href="{{ route('register') }}">Register</a></li>
|
||||
@else
|
||||
<li class="dropdown">
|
||||
<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false" aria-haspopup="true" v-pre>
|
||||
{{ Auth::user()->name }} <span class="caret"></span>
|
||||
</a>
|
||||
|
||||
<ul class="dropdown-menu">
|
||||
<li>
|
||||
<a href="{{ route('logout') }}"
|
||||
onclick="event.preventDefault();
|
||||
document.getElementById('logout-form').submit();">
|
||||
Logout
|
||||
</a>
|
||||
|
||||
<form id="logout-form" action="{{ route('logout') }}" method="POST" style="display: none;">
|
||||
{{ csrf_field() }}
|
||||
</form>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
@endguest
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="collapse navbar-collapse" id="app-navbar-collapse">
|
||||
<!-- Left Side Of Navbar -->
|
||||
<ul class="nav navbar-nav">
|
||||
<li><a href="{{ url('/home') }}">Home</a></li>
|
||||
</ul>
|
||||
@yield('content')
|
||||
</div>
|
||||
|
||||
<!-- Right Side Of Navbar -->
|
||||
<ul class="nav navbar-nav navbar-right">
|
||||
<!-- Authentication Links -->
|
||||
@if (Auth::guest())
|
||||
<li><a href="{{ url('/login') }}">Login</a></li>
|
||||
<li><a href="{{ url('/register') }}">Register</a></li>
|
||||
@else
|
||||
<li class="dropdown">
|
||||
<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">
|
||||
{{ Auth::user()->name }} <span class="caret"></span>
|
||||
</a>
|
||||
|
||||
<ul class="dropdown-menu" role="menu">
|
||||
<li><a href="{{ url('/logout') }}"><i class="fa fa-btn fa-sign-out"></i>Logout</a></li>
|
||||
</ul>
|
||||
</li>
|
||||
@endif
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
@yield('content')
|
||||
|
||||
<!-- JavaScripts -->
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.2.3/jquery.min.js" integrity="sha384-I6F5OKECLVtK/BL+8iSLDEHowSAfUo76ZL9+kGAgTRdiByINKJaqTPH/QVNS1VDb" crossorigin="anonymous"></script>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.3.6/js/bootstrap.min.js" integrity="sha384-0mSbJDEHialfmuBBQP6A4Qrprq5OVfW37PRR3j5ELqxss1yVqOtnepnHVP9aJ7xS" crossorigin="anonymous"></script>
|
||||
{{-- <script src="{{ elixir('js/app.js') }}"></script> --}}
|
||||
<!-- Scripts -->
|
||||
<script src="{{ asset('js/app.js') }}"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
@@ -1,17 +0,0 @@
|
||||
@extends('layouts.app')
|
||||
|
||||
@section('content')
|
||||
<div class="container">
|
||||
<div class="row">
|
||||
<div class="col-md-10 col-md-offset-1">
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading">Welcome</div>
|
||||
|
||||
<div class="panel-body">
|
||||
Your Application's Landing Page.
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@endsection
|
@@ -16,28 +16,45 @@ 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']) {
|
||||
switch ($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.");
|
||||
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];
|
||||
}
|
||||
}
|
||||
|
||||
@@ -64,4 +81,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'];
|
||||
}
|
||||
}
|
||||
|
@@ -68,12 +68,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->conn->table($this->table)->find($identifier)
|
||||
);
|
||||
|
||||
return $this->getGenericUser($user);
|
||||
return $user && $user->getRememberToken() && hash_equals($user->getRememberToken(), $token)
|
||||
? $user : null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -86,8 +86,8 @@ class DatabaseUserProvider implements UserProvider
|
||||
public function updateRememberToken(UserContract $user, $token)
|
||||
{
|
||||
$this->conn->table($this->table)
|
||||
->where('id', $user->getAuthIdentifier())
|
||||
->update(['remember_token' => $token]);
|
||||
->where($user->getAuthIdentifierName(), $user->getAuthIdentifier())
|
||||
->update([$user->getRememberTokenName() => $token]);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -98,6 +98,12 @@ class DatabaseUserProvider implements UserProvider
|
||||
*/
|
||||
public function retrieveByCredentials(array $credentials)
|
||||
{
|
||||
if (empty($credentials) ||
|
||||
(count($credentials) === 1 &&
|
||||
array_key_exists('password', $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.
|
||||
@@ -125,7 +131,7 @@ class DatabaseUserProvider implements UserProvider
|
||||
*/
|
||||
protected function getGenericUser($user)
|
||||
{
|
||||
if ($user !== null) {
|
||||
if (! is_null($user)) {
|
||||
return new GenericUser((array) $user);
|
||||
}
|
||||
}
|
||||
@@ -139,8 +145,8 @@ class DatabaseUserProvider implements UserProvider
|
||||
*/
|
||||
public function validateCredentials(UserContract $user, array $credentials)
|
||||
{
|
||||
$plain = $credentials['password'];
|
||||
|
||||
return $this->hasher->check($plain, $user->getAuthPassword());
|
||||
return $this->hasher->check(
|
||||
$credentials['password'], $user->getAuthPassword()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@@ -44,7 +44,11 @@ class EloquentUserProvider implements UserProvider
|
||||
*/
|
||||
public function retrieveById($identifier)
|
||||
{
|
||||
return $this->createModel()->newQuery()->find($identifier);
|
||||
$model = $this->createModel();
|
||||
|
||||
return $model->newQuery()
|
||||
->where($model->getAuthIdentifierName(), $identifier)
|
||||
->first();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -58,10 +62,15 @@ class EloquentUserProvider implements UserProvider
|
||||
{
|
||||
$model = $this->createModel();
|
||||
|
||||
return $model->newQuery()
|
||||
->where($model->getAuthIdentifierName(), $identifier)
|
||||
->where($model->getRememberTokenName(), $token)
|
||||
->first();
|
||||
$model = $model->where($model->getAuthIdentifierName(), $identifier)->first();
|
||||
|
||||
if (! $model) {
|
||||
return null;
|
||||
}
|
||||
|
||||
$rememberToken = $model->getRememberToken();
|
||||
|
||||
return $rememberToken && hash_equals($rememberToken, $token) ? $model : null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -75,7 +84,13 @@ class EloquentUserProvider implements UserProvider
|
||||
{
|
||||
$user->setRememberToken($token);
|
||||
|
||||
$timestamps = $user->timestamps;
|
||||
|
||||
$user->timestamps = false;
|
||||
|
||||
$user->save();
|
||||
|
||||
$user->timestamps = $timestamps;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -86,7 +101,9 @@ class EloquentUserProvider implements UserProvider
|
||||
*/
|
||||
public function retrieveByCredentials(array $credentials)
|
||||
{
|
||||
if (empty($credentials)) {
|
||||
if (empty($credentials) ||
|
||||
(count($credentials) === 1 &&
|
||||
array_key_exists('password', $credentials))) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
@@ -18,23 +18,15 @@ class Attempting
|
||||
*/
|
||||
public $remember;
|
||||
|
||||
/**
|
||||
* Indicates if the user should be authenticated if successful.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
public $login;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @param bool $remember
|
||||
* @param bool $login
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($credentials, $remember, $login)
|
||||
public function __construct($credentials, $remember)
|
||||
{
|
||||
$this->login = $login;
|
||||
$this->remember = $remember;
|
||||
$this->credentials = $credentials;
|
||||
}
|
||||
|
28
vendor/laravel/framework/src/Illuminate/Auth/Events/Authenticated.php
vendored
Normal file
28
vendor/laravel/framework/src/Illuminate/Auth/Events/Authenticated.php
vendored
Normal file
@@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Events;
|
||||
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class Authenticated
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The authenticated 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;
|
||||
}
|
||||
}
|
@@ -23,6 +23,7 @@ class Failed
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param array $credentials
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($user, $credentials)
|
||||
{
|
||||
|
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;
|
||||
}
|
||||
}
|
28
vendor/laravel/framework/src/Illuminate/Auth/Events/Registered.php
vendored
Normal file
28
vendor/laravel/framework/src/Illuminate/Auth/Events/Registered.php
vendored
Normal file
@@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Events;
|
||||
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
|
||||
class Registered
|
||||
{
|
||||
use SerializesModels;
|
||||
|
||||
/**
|
||||
* The authenticated 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;
|
||||
}
|
||||
}
|
@@ -2,6 +2,7 @@
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Contracts\Auth\Authenticatable as AuthenticatableContract;
|
||||
|
||||
/**
|
||||
@@ -36,7 +37,7 @@ trait GuardHelpers
|
||||
return $user;
|
||||
}
|
||||
|
||||
throw new AuthenticationException($this);
|
||||
throw new AuthenticationException;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -83,4 +84,25 @@ trait GuardHelpers
|
||||
|
||||
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;
|
||||
}
|
||||
}
|
||||
|
68
vendor/laravel/framework/src/Illuminate/Auth/Middleware/Authenticate.php
vendored
Normal file
68
vendor/laravel/framework/src/Illuminate/Auth/Middleware/Authenticate.php
vendored
Normal file
@@ -0,0 +1,68 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Auth\AuthenticationException;
|
||||
use Illuminate\Contracts\Auth\Factory as Auth;
|
||||
|
||||
class Authenticate
|
||||
{
|
||||
/**
|
||||
* The authentication factory instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Factory
|
||||
*/
|
||||
protected $auth;
|
||||
|
||||
/**
|
||||
* Create a new middleware instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Factory $auth
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Auth $auth)
|
||||
{
|
||||
$this->auth = $auth;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @param string[] ...$guards
|
||||
* @return mixed
|
||||
*
|
||||
* @throws \Illuminate\Auth\AuthenticationException
|
||||
*/
|
||||
public function handle($request, Closure $next, ...$guards)
|
||||
{
|
||||
$this->authenticate($guards);
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the user is logged in to any of the given guards.
|
||||
*
|
||||
* @param array $guards
|
||||
* @return void
|
||||
*
|
||||
* @throws \Illuminate\Auth\AuthenticationException
|
||||
*/
|
||||
protected function authenticate(array $guards)
|
||||
{
|
||||
if (empty($guards)) {
|
||||
return $this->auth->authenticate();
|
||||
}
|
||||
|
||||
foreach ($guards as $guard) {
|
||||
if ($this->auth->guard($guard)->check()) {
|
||||
return $this->auth->shouldUse($guard);
|
||||
}
|
||||
}
|
||||
|
||||
throw new AuthenticationException('Unauthenticated.', $guards);
|
||||
}
|
||||
}
|
100
vendor/laravel/framework/src/Illuminate/Auth/Middleware/Authorize.php
vendored
Normal file
100
vendor/laravel/framework/src/Illuminate/Auth/Middleware/Authorize.php
vendored
Normal file
@@ -0,0 +1,100 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Database\Eloquent\Model;
|
||||
use Illuminate\Contracts\Auth\Access\Gate;
|
||||
use Illuminate\Contracts\Auth\Factory as Auth;
|
||||
|
||||
class Authorize
|
||||
{
|
||||
/**
|
||||
* The authentication factory instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Factory
|
||||
*/
|
||||
protected $auth;
|
||||
|
||||
/**
|
||||
* The gate instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Auth\Access\Gate
|
||||
*/
|
||||
protected $gate;
|
||||
|
||||
/**
|
||||
* 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)
|
||||
{
|
||||
$this->auth = $auth;
|
||||
$this->gate = $gate;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @param string $ability
|
||||
* @param array|null $models
|
||||
* @return mixed
|
||||
*
|
||||
* @throws \Illuminate\Auth\AuthenticationException
|
||||
* @throws \Illuminate\Auth\Access\AuthorizationException
|
||||
*/
|
||||
public function handle($request, Closure $next, $ability, ...$models)
|
||||
{
|
||||
$this->auth->authenticate();
|
||||
|
||||
$this->gate->authorize($ability, $this->getGateArguments($request, $models));
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the arguments parameter for the gate.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param array|null $models
|
||||
* @return array|string|\Illuminate\Database\Eloquent\Model
|
||||
*/
|
||||
protected function getGateArguments($request, $models)
|
||||
{
|
||||
if (is_null($models)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
return collect($models)->map(function ($model) use ($request) {
|
||||
return $model instanceof Model ? $model : $this->getModel($request, $model);
|
||||
})->all();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the model to authorize.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param string $model
|
||||
* @return \Illuminate\Database\Eloquent\Model|string
|
||||
*/
|
||||
protected function getModel($request, $model)
|
||||
{
|
||||
return $this->isClassName($model) ? $model : $request->route($model);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if the given string looks like a fully qualified class name.
|
||||
*
|
||||
* @param string $value
|
||||
* @return bool
|
||||
*/
|
||||
protected function isClassName($value)
|
||||
{
|
||||
return strpos($value, '\\') !== false;
|
||||
}
|
||||
}
|
52
vendor/laravel/framework/src/Illuminate/Auth/Notifications/ResetPassword.php
vendored
Normal file
52
vendor/laravel/framework/src/Illuminate/Auth/Notifications/ResetPassword.php
vendored
Normal file
@@ -0,0 +1,52 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth\Notifications;
|
||||
|
||||
use Illuminate\Notifications\Notification;
|
||||
use Illuminate\Notifications\Messages\MailMessage;
|
||||
|
||||
class ResetPassword extends Notification
|
||||
{
|
||||
/**
|
||||
* The password reset token.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $token;
|
||||
|
||||
/**
|
||||
* Create a notification instance.
|
||||
*
|
||||
* @param string $token
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($token)
|
||||
{
|
||||
$this->token = $token;
|
||||
}
|
||||
|
||||
/**
|
||||
* 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)
|
||||
{
|
||||
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.');
|
||||
}
|
||||
}
|
@@ -2,6 +2,8 @@
|
||||
|
||||
namespace Illuminate\Auth\Passwords;
|
||||
|
||||
use Illuminate\Auth\Notifications\ResetPassword as ResetPasswordNotification;
|
||||
|
||||
trait CanResetPassword
|
||||
{
|
||||
/**
|
||||
@@ -13,4 +15,15 @@ trait CanResetPassword
|
||||
{
|
||||
return $this->email;
|
||||
}
|
||||
|
||||
/**
|
||||
* Send the password reset notification.
|
||||
*
|
||||
* @param string $token
|
||||
* @return void
|
||||
*/
|
||||
public function sendPasswordResetNotification($token)
|
||||
{
|
||||
$this->notify(new ResetPasswordNotification($token));
|
||||
}
|
||||
}
|
||||
|
@@ -2,9 +2,10 @@
|
||||
|
||||
namespace Illuminate\Auth\Passwords;
|
||||
|
||||
use Carbon\Carbon;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Support\Carbon;
|
||||
use Illuminate\Database\ConnectionInterface;
|
||||
use Illuminate\Contracts\Hashing\Hasher as HasherContract;
|
||||
use Illuminate\Contracts\Auth\CanResetPassword as CanResetPasswordContract;
|
||||
|
||||
class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
@@ -16,6 +17,13 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
*/
|
||||
protected $connection;
|
||||
|
||||
/**
|
||||
* The Hasher implementation.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Hashing\Hasher
|
||||
*/
|
||||
protected $hasher;
|
||||
|
||||
/**
|
||||
* The token database table.
|
||||
*
|
||||
@@ -41,14 +49,17 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
* Create a new token repository instance.
|
||||
*
|
||||
* @param \Illuminate\Database\ConnectionInterface $connection
|
||||
* @param \Illuminate\Contracts\Hashing\Hasher $hasher
|
||||
* @param string $table
|
||||
* @param string $hashKey
|
||||
* @param int $expires
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(ConnectionInterface $connection, $table, $hashKey, $expires = 60)
|
||||
public function __construct(ConnectionInterface $connection, HasherContract $hasher,
|
||||
$table, $hashKey, $expires = 60)
|
||||
{
|
||||
$this->table = $table;
|
||||
$this->hasher = $hasher;
|
||||
$this->hashKey = $hashKey;
|
||||
$this->expires = $expires * 60;
|
||||
$this->connection = $connection;
|
||||
@@ -96,7 +107,7 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
*/
|
||||
protected function getPayload($email, $token)
|
||||
{
|
||||
return ['email' => $email, 'token' => $token, 'created_at' => new Carbon];
|
||||
return ['email' => $email, 'token' => $this->hasher->make($token), 'created_at' => new Carbon];
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -108,35 +119,35 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
*/
|
||||
public function exists(CanResetPasswordContract $user, $token)
|
||||
{
|
||||
$email = $user->getEmailForPasswordReset();
|
||||
$record = (array) $this->getTable()->where(
|
||||
'email', $user->getEmailForPasswordReset()
|
||||
)->first();
|
||||
|
||||
$token = (array) $this->getTable()->where('email', $email)->where('token', $token)->first();
|
||||
|
||||
return $token && ! $this->tokenExpired($token);
|
||||
return $record &&
|
||||
! $this->tokenExpired($record['created_at']) &&
|
||||
$this->hasher->check($token, $record['token']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the token has expired.
|
||||
*
|
||||
* @param array $token
|
||||
* @param string $createdAt
|
||||
* @return bool
|
||||
*/
|
||||
protected function tokenExpired($token)
|
||||
protected function tokenExpired($createdAt)
|
||||
{
|
||||
$expiresAt = Carbon::parse($token['created_at'])->addSeconds($this->expires);
|
||||
|
||||
return $expiresAt->isPast();
|
||||
return Carbon::parse($createdAt)->addSeconds($this->expires)->isPast();
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete a token record by token.
|
||||
* Delete a token record by user.
|
||||
*
|
||||
* @param string $token
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @return void
|
||||
*/
|
||||
public function delete($token)
|
||||
public function delete(CanResetPasswordContract $user)
|
||||
{
|
||||
$this->getTable()->where('token', $token)->delete();
|
||||
$this->deleteExisting($user);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -161,6 +172,16 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
return hash_hmac('sha256', Str::random(40), $this->hashKey);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the database connection instance.
|
||||
*
|
||||
* @return \Illuminate\Database\ConnectionInterface
|
||||
*/
|
||||
public function getConnection()
|
||||
{
|
||||
return $this->connection;
|
||||
}
|
||||
|
||||
/**
|
||||
* Begin a new database query against the table.
|
||||
*
|
||||
@@ -172,12 +193,12 @@ class DatabaseTokenRepository implements TokenRepositoryInterface
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the database connection instance.
|
||||
* Get the hasher instance.
|
||||
*
|
||||
* @return \Illuminate\Database\ConnectionInterface
|
||||
* @return \Illuminate\Contracts\Hashing\Hasher
|
||||
*/
|
||||
public function getConnection()
|
||||
public function getHasher()
|
||||
{
|
||||
return $this->connection;
|
||||
return $this->hasher;
|
||||
}
|
||||
}
|
||||
|
@@ -6,7 +6,6 @@ use Closure;
|
||||
use Illuminate\Support\Arr;
|
||||
use UnexpectedValueException;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
use Illuminate\Contracts\Mail\Mailer as MailerContract;
|
||||
use Illuminate\Contracts\Auth\PasswordBroker as PasswordBrokerContract;
|
||||
use Illuminate\Contracts\Auth\CanResetPassword as CanResetPasswordContract;
|
||||
|
||||
@@ -26,20 +25,6 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
*/
|
||||
protected $users;
|
||||
|
||||
/**
|
||||
* The mailer instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Mail\Mailer
|
||||
*/
|
||||
protected $mailer;
|
||||
|
||||
/**
|
||||
* The view of the password reset link e-mail.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $emailView;
|
||||
|
||||
/**
|
||||
* The custom password validator callback.
|
||||
*
|
||||
@@ -52,29 +37,22 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
*
|
||||
* @param \Illuminate\Auth\Passwords\TokenRepositoryInterface $tokens
|
||||
* @param \Illuminate\Contracts\Auth\UserProvider $users
|
||||
* @param \Illuminate\Contracts\Mail\Mailer $mailer
|
||||
* @param string $emailView
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(TokenRepositoryInterface $tokens,
|
||||
UserProvider $users,
|
||||
MailerContract $mailer,
|
||||
$emailView)
|
||||
UserProvider $users)
|
||||
{
|
||||
$this->users = $users;
|
||||
$this->mailer = $mailer;
|
||||
$this->tokens = $tokens;
|
||||
$this->emailView = $emailView;
|
||||
}
|
||||
|
||||
/**
|
||||
* Send a password reset link to a user.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @param \Closure|null $callback
|
||||
* @return string
|
||||
*/
|
||||
public function sendResetLink(array $credentials, Closure $callback = null)
|
||||
public function sendResetLink(array $credentials)
|
||||
{
|
||||
// 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
|
||||
@@ -88,37 +66,13 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
// 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.
|
||||
$token = $this->tokens->create($user);
|
||||
|
||||
$this->emailResetLink($user, $token, $callback);
|
||||
$user->sendPasswordResetNotification(
|
||||
$this->tokens->create($user)
|
||||
);
|
||||
|
||||
return static::RESET_LINK_SENT;
|
||||
}
|
||||
|
||||
/**
|
||||
* Send the password reset link via e-mail.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @param string $token
|
||||
* @param \Closure|null $callback
|
||||
* @return int
|
||||
*/
|
||||
public function emailResetLink(CanResetPasswordContract $user, $token, Closure $callback = null)
|
||||
{
|
||||
// We will use the reminder view that was given to the broker to display the
|
||||
// password reminder e-mail. We'll pass a "token" variable into the views
|
||||
// so that it may be displayed for an user to click for password reset.
|
||||
$view = $this->emailView;
|
||||
|
||||
return $this->mailer->send($view, compact('token', 'user'), function ($m) use ($user, $token, $callback) {
|
||||
$m->to($user->getEmailForPasswordReset());
|
||||
|
||||
if (! is_null($callback)) {
|
||||
call_user_func($callback, $m, $user, $token);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reset the password for the given token.
|
||||
*
|
||||
@@ -137,14 +91,14 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
return $user;
|
||||
}
|
||||
|
||||
$pass = $credentials['password'];
|
||||
$password = $credentials['password'];
|
||||
|
||||
// Once we have called this callback, we will remove this token row from the
|
||||
// table and return the response from this callback so the user gets sent
|
||||
// to the destination given by the developers from the callback return.
|
||||
call_user_func($callback, $user, $pass);
|
||||
// Once the reset has been validated, we'll call the given callback with the
|
||||
// new password. This gives the user an opportunity to store the password
|
||||
// in their persistent storage. Then we'll delete the token and return.
|
||||
$callback($user, $password);
|
||||
|
||||
$this->tokens->delete($credentials['token']);
|
||||
$this->tokens->delete($user);
|
||||
|
||||
return static::PASSWORD_RESET;
|
||||
}
|
||||
@@ -153,7 +107,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)
|
||||
{
|
||||
@@ -191,14 +145,15 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
*/
|
||||
public function validateNewPassword(array $credentials)
|
||||
{
|
||||
list($password, $confirm) = [
|
||||
$credentials['password'],
|
||||
$credentials['password_confirmation'],
|
||||
];
|
||||
|
||||
if (isset($this->passwordValidator)) {
|
||||
list($password, $confirm) = [
|
||||
$credentials['password'],
|
||||
$credentials['password_confirmation'],
|
||||
];
|
||||
|
||||
return call_user_func(
|
||||
$this->passwordValidator, $credentials) && $password === $confirm;
|
||||
$this->passwordValidator, $credentials
|
||||
) && $password === $confirm;
|
||||
}
|
||||
|
||||
return $this->validatePasswordWithDefaults($credentials);
|
||||
@@ -224,7 +179,7 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
* Get the user for the given credentials.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @return \Illuminate\Contracts\Auth\CanResetPassword
|
||||
* @return \Illuminate\Contracts\Auth\CanResetPassword|null
|
||||
*
|
||||
* @throws \UnexpectedValueException
|
||||
*/
|
||||
@@ -244,7 +199,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)
|
||||
@@ -253,20 +208,20 @@ class PasswordBroker implements PasswordBrokerContract
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete the given password reset token.
|
||||
* Delete password reset tokens of the given user.
|
||||
*
|
||||
* @param string $token
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @return void
|
||||
*/
|
||||
public function deleteToken($token)
|
||||
public function deleteToken(CanResetPasswordContract $user)
|
||||
{
|
||||
$this->tokens->delete($token);
|
||||
$this->tokens->delete($user);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate the given password reset token.
|
||||
*
|
||||
* @param CanResetPasswordContract $user
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @param string $token
|
||||
* @return bool
|
||||
*/
|
||||
|
@@ -6,6 +6,9 @@ use Illuminate\Support\Str;
|
||||
use InvalidArgumentException;
|
||||
use Illuminate\Contracts\Auth\PasswordBrokerFactory as FactoryContract;
|
||||
|
||||
/**
|
||||
* @mixin \Illuminate\Contracts\Auth\PasswordBroker
|
||||
*/
|
||||
class PasswordBrokerManager implements FactoryContract
|
||||
{
|
||||
/**
|
||||
@@ -69,9 +72,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['mailer'],
|
||||
$config['email']
|
||||
$this->app['auth']->createUserProvider($config['provider'] ?? null)
|
||||
);
|
||||
}
|
||||
|
||||
@@ -89,10 +90,11 @@ class PasswordBrokerManager implements FactoryContract
|
||||
$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']
|
||||
@@ -140,6 +142,6 @@ class PasswordBrokerManager implements FactoryContract
|
||||
*/
|
||||
public function __call($method, $parameters)
|
||||
{
|
||||
return call_user_func_array([$this->broker(), $method], $parameters);
|
||||
return $this->broker()->{$method}(...$parameters);
|
||||
}
|
||||
}
|
||||
|
@@ -26,10 +26,10 @@ interface TokenRepositoryInterface
|
||||
/**
|
||||
* Delete a token record.
|
||||
*
|
||||
* @param string $token
|
||||
* @param \Illuminate\Contracts\Auth\CanResetPassword $user
|
||||
* @return void
|
||||
*/
|
||||
public function delete($token);
|
||||
public function delete(CanResetPasswordContract $user);
|
||||
|
||||
/**
|
||||
* Delete expired tokens.
|
||||
|
88
vendor/laravel/framework/src/Illuminate/Auth/Recaller.php
vendored
Normal file
88
vendor/laravel/framework/src/Illuminate/Auth/Recaller.php
vendored
Normal file
@@ -0,0 +1,88 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Support\Str;
|
||||
|
||||
class Recaller
|
||||
{
|
||||
/**
|
||||
* The "recaller" / "remember me" cookie string.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $recaller;
|
||||
|
||||
/**
|
||||
* Create a new recaller instance.
|
||||
*
|
||||
* @param string $recaller
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($recaller)
|
||||
{
|
||||
$this->recaller = $recaller;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the user ID from the recaller.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function id()
|
||||
{
|
||||
return explode('|', $this->recaller, 3)[0];
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the "remember token" token from the recaller.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function token()
|
||||
{
|
||||
return explode('|', $this->recaller, 3)[1];
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the password from the recaller.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function hash()
|
||||
{
|
||||
return explode('|', $this->recaller, 3)[2];
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the recaller is valid.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function valid()
|
||||
{
|
||||
return $this->properString() && $this->hasAllSegments();
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the recaller is an invalid string.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
protected function properString()
|
||||
{
|
||||
return is_string($this->recaller) && Str::contains($this->recaller, '|');
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the recaller has all segments.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
protected function hasAllSegments()
|
||||
{
|
||||
$segments = explode('|', $this->recaller);
|
||||
|
||||
return count($segments) == 3 && trim($segments[0]) !== '' && trim($segments[1]) !== '';
|
||||
}
|
||||
}
|
@@ -4,10 +4,12 @@ namespace Illuminate\Auth;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Contracts\Auth\Guard;
|
||||
use Illuminate\Support\Traits\Macroable;
|
||||
use Illuminate\Contracts\Auth\UserProvider;
|
||||
|
||||
class RequestGuard implements Guard
|
||||
{
|
||||
use GuardHelpers;
|
||||
use GuardHelpers, Macroable;
|
||||
|
||||
/**
|
||||
* The guard callback.
|
||||
@@ -28,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;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -50,7 +54,9 @@ class RequestGuard implements Guard
|
||||
return $this->user;
|
||||
}
|
||||
|
||||
return $this->user = call_user_func($this->callback, $this->request);
|
||||
return $this->user = call_user_func(
|
||||
$this->callback, $this->request, $this->getProvider()
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -62,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());
|
||||
}
|
||||
|
||||
|
@@ -4,24 +4,25 @@ namespace Illuminate\Auth;
|
||||
|
||||
use RuntimeException;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Http\Response;
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
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 Symfony\Component\HttpFoundation\Session\SessionInterface;
|
||||
use Symfony\Component\HttpKernel\Exception\UnauthorizedHttpException;
|
||||
use Illuminate\Contracts\Auth\Authenticatable as AuthenticatableContract;
|
||||
|
||||
class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
{
|
||||
use GuardHelpers;
|
||||
use GuardHelpers, Macroable;
|
||||
|
||||
/**
|
||||
* The name of the Guard. Typically "session".
|
||||
*
|
||||
* Corresponds to driver name in authentication configuration.
|
||||
* Corresponds to guard name in authentication configuration.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
@@ -44,7 +45,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
/**
|
||||
* The session used by the guard.
|
||||
*
|
||||
* @var \Symfony\Component\HttpFoundation\Session\SessionInterface
|
||||
* @var \Illuminate\Contracts\Session\Session
|
||||
*/
|
||||
protected $session;
|
||||
|
||||
@@ -81,20 +82,20 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
protected $tokenRetrievalAttempted = false;
|
||||
protected $recallAttempted = false;
|
||||
|
||||
/**
|
||||
* Create a new authentication guard.
|
||||
*
|
||||
* @param string $name
|
||||
* @param \Illuminate\Contracts\Auth\UserProvider $provider
|
||||
* @param \Symfony\Component\HttpFoundation\Session\SessionInterface $session
|
||||
* @param \Illuminate\Contracts\Session\Session $session
|
||||
* @param \Symfony\Component\HttpFoundation\Request $request
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($name,
|
||||
UserProvider $provider,
|
||||
SessionInterface $session,
|
||||
Session $session,
|
||||
Request $request = null)
|
||||
{
|
||||
$this->name = $name;
|
||||
@@ -126,28 +127,68 @@ 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)) {
|
||||
$user = $this->provider->retrieveById($id);
|
||||
if ($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->getRecaller();
|
||||
$recaller = $this->recaller();
|
||||
|
||||
if (is_null($user) && ! is_null($recaller)) {
|
||||
$user = $this->getUserByRecaller($recaller);
|
||||
if (is_null($this->user) && ! is_null($recaller)) {
|
||||
$this->user = $this->userFromRecaller($recaller);
|
||||
|
||||
if ($user) {
|
||||
$this->updateSession($user->getAuthIdentifier());
|
||||
if ($this->user) {
|
||||
$this->updateSession($this->user->getAuthIdentifier());
|
||||
|
||||
$this->fireLoginEvent($user, true);
|
||||
$this->fireLoginEvent($this->user, true);
|
||||
}
|
||||
}
|
||||
|
||||
return $this->user = $user;
|
||||
return $this->user;
|
||||
}
|
||||
|
||||
/**
|
||||
* Pull a user from the repository by its "remember me" cookie token.
|
||||
*
|
||||
* @param \Illuminate\Auth\Recaller $recaller
|
||||
* @return mixed
|
||||
*/
|
||||
protected function userFromRecaller($recaller)
|
||||
{
|
||||
if (! $recaller->valid() || $this->recallAttempted) {
|
||||
return;
|
||||
}
|
||||
|
||||
// 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.
|
||||
$this->recallAttempted = true;
|
||||
|
||||
$this->viaRemember = ! is_null($user = $this->provider->retrieveByToken(
|
||||
$recaller->id(), $recaller->token()
|
||||
));
|
||||
|
||||
return $user;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the decrypted recaller cookie for the request.
|
||||
*
|
||||
* @return \Illuminate\Auth\Recaller|null
|
||||
*/
|
||||
protected function recaller()
|
||||
{
|
||||
if (is_null($this->request)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if ($recaller = $this->request->cookies->get($this->getRecallerName())) {
|
||||
return new Recaller($recaller);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -161,71 +202,9 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
return;
|
||||
}
|
||||
|
||||
$id = $this->session->get($this->getName());
|
||||
|
||||
if (is_null($id) && $this->user()) {
|
||||
$id = $this->user()->getAuthIdentifier();
|
||||
}
|
||||
|
||||
return $id;
|
||||
}
|
||||
|
||||
/**
|
||||
* Pull a user from the repository by its recaller ID.
|
||||
*
|
||||
* @param string $recaller
|
||||
* @return mixed
|
||||
*/
|
||||
protected function getUserByRecaller($recaller)
|
||||
{
|
||||
if ($this->validRecaller($recaller) && ! $this->tokenRetrievalAttempted) {
|
||||
$this->tokenRetrievalAttempted = true;
|
||||
|
||||
list($id, $token) = explode('|', $recaller, 2);
|
||||
|
||||
$this->viaRemember = ! is_null($user = $this->provider->retrieveByToken($id, $token));
|
||||
|
||||
return $user;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the decrypted recaller cookie for the request.
|
||||
*
|
||||
* @return string|null
|
||||
*/
|
||||
protected function getRecaller()
|
||||
{
|
||||
return $this->request->cookies->get($this->getRecallerName());
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the user ID from the recaller cookie.
|
||||
*
|
||||
* @return string|null
|
||||
*/
|
||||
protected function getRecallerId()
|
||||
{
|
||||
if ($this->validRecaller($recaller = $this->getRecaller())) {
|
||||
return head(explode('|', $recaller));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the recaller cookie is in a valid format.
|
||||
*
|
||||
* @param mixed $recaller
|
||||
* @return bool
|
||||
*/
|
||||
protected function validRecaller($recaller)
|
||||
{
|
||||
if (! is_string($recaller) || ! Str::contains($recaller, '|')) {
|
||||
return false;
|
||||
}
|
||||
|
||||
$segments = explode('|', $recaller);
|
||||
|
||||
return count($segments) == 2 && trim($segments[0]) !== '' && trim($segments[1]) !== '';
|
||||
return $this->user()
|
||||
? $this->user()->getAuthIdentifier()
|
||||
: $this->session->get($this->getName());
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -236,6 +215,8 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
public function once(array $credentials = [])
|
||||
{
|
||||
$this->fireAttemptEvent($credentials);
|
||||
|
||||
if ($this->validate($credentials)) {
|
||||
$this->setUser($this->lastAttempted);
|
||||
|
||||
@@ -245,6 +226,23 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Log the given user ID into the application without sessions or cookies.
|
||||
*
|
||||
* @param mixed $id
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable|false
|
||||
*/
|
||||
public function onceUsingId($id)
|
||||
{
|
||||
if (! is_null($user = $this->provider->retrieveById($id))) {
|
||||
$this->setUser($user);
|
||||
|
||||
return $user;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate a user's credentials.
|
||||
*
|
||||
@@ -253,7 +251,9 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
public function validate(array $credentials = [])
|
||||
{
|
||||
return $this->attempt($credentials, false, false);
|
||||
$this->lastAttempted = $user = $this->provider->retrieveByCredentials($credentials);
|
||||
|
||||
return $this->hasValidCredentials($user, $credentials);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -276,7 +276,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
return;
|
||||
}
|
||||
|
||||
return $this->getBasicResponse();
|
||||
return $this->failedBasicResponse();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -288,10 +288,10 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
public function onceBasic($field = 'email', $extraConditions = [])
|
||||
{
|
||||
$credentials = $this->getBasicCredentials($this->getRequest(), $field);
|
||||
$credentials = $this->basicCredentials($this->getRequest(), $field);
|
||||
|
||||
if (! $this->once(array_merge($credentials, $extraConditions))) {
|
||||
return $this->getBasicResponse();
|
||||
return $this->failedBasicResponse();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -309,9 +309,9 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
return false;
|
||||
}
|
||||
|
||||
$credentials = $this->getBasicCredentials($request, $field);
|
||||
|
||||
return $this->attempt(array_merge($credentials, $extraConditions));
|
||||
return $this->attempt(array_merge(
|
||||
$this->basicCredentials($request, $field), $extraConditions
|
||||
));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -321,7 +321,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
* @param string $field
|
||||
* @return array
|
||||
*/
|
||||
protected function getBasicCredentials(Request $request, $field)
|
||||
protected function basicCredentials(Request $request, $field)
|
||||
{
|
||||
return [$field => $request->getUser(), 'password' => $request->getPassword()];
|
||||
}
|
||||
@@ -329,13 +329,12 @@ 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 getBasicResponse()
|
||||
protected function failedBasicResponse()
|
||||
{
|
||||
$headers = ['WWW-Authenticate' => 'Basic'];
|
||||
|
||||
return new Response('Invalid credentials.', 401, $headers);
|
||||
throw new UnauthorizedHttpException('Basic', 'Invalid credentials.');
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -343,12 +342,11 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*
|
||||
* @param array $credentials
|
||||
* @param bool $remember
|
||||
* @param bool $login
|
||||
* @return bool
|
||||
*/
|
||||
public function attempt(array $credentials = [], $remember = false, $login = true)
|
||||
public function attempt(array $credentials = [], $remember = false)
|
||||
{
|
||||
$this->fireAttemptEvent($credentials, $remember, $login);
|
||||
$this->fireAttemptEvent($credentials, $remember);
|
||||
|
||||
$this->lastAttempted = $user = $this->provider->retrieveByCredentials($credentials);
|
||||
|
||||
@@ -356,9 +354,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
// to validate the user against the given credentials, and if they are in
|
||||
// fact valid we'll log the users into the application and return true.
|
||||
if ($this->hasValidCredentials($user, $credentials)) {
|
||||
if ($login) {
|
||||
$this->login($user, $remember);
|
||||
}
|
||||
$this->login($user, $remember);
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -366,9 +362,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
// If the authentication attempt fails we will fire an event so that the user
|
||||
// may be notified of any suspicious attempts to access their account from
|
||||
// an unrecognized user. A developer may listen to this event as needed.
|
||||
if ($login) {
|
||||
$this->fireFailedEvent($user, $credentials);
|
||||
}
|
||||
$this->fireFailedEvent($user, $credentials);
|
||||
|
||||
return false;
|
||||
}
|
||||
@@ -386,47 +380,21 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire the attempt event with the arguments.
|
||||
* Log the given user ID into the application.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @param bool $remember
|
||||
* @param bool $login
|
||||
* @return void
|
||||
* @param mixed $id
|
||||
* @param bool $remember
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable|false
|
||||
*/
|
||||
protected function fireAttemptEvent(array $credentials, $remember, $login)
|
||||
public function loginUsingId($id, $remember = false)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->fire(new Events\Attempting(
|
||||
$credentials, $remember, $login
|
||||
));
|
||||
}
|
||||
}
|
||||
if (! is_null($user = $this->provider->retrieveById($id))) {
|
||||
$this->login($user, $remember);
|
||||
|
||||
/**
|
||||
* Fire the failed authentication attempt event with the given arguments.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param array $credentials
|
||||
* @return void
|
||||
*/
|
||||
protected function fireFailedEvent($user, array $credentials)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->fire(new Events\Failed($user, $credentials));
|
||||
return $user;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Register an authentication attempt event listener.
|
||||
*
|
||||
* @param mixed $callback
|
||||
* @return void
|
||||
*/
|
||||
public function attempting($callback)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->listen(Events\Attempting::class, $callback);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -444,7 +412,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
// queue a permanent cookie that contains the encrypted copy of the user
|
||||
// identifier. We will then decrypt this later to retrieve the users.
|
||||
if ($remember) {
|
||||
$this->createRememberTokenIfDoesntExist($user);
|
||||
$this->ensureRememberTokenIsSet($user);
|
||||
|
||||
$this->queueRecallerCookie($user);
|
||||
}
|
||||
@@ -457,20 +425,6 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
$this->setUser($user);
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire the login event if the dispatcher is set.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param bool $remember
|
||||
* @return void
|
||||
*/
|
||||
protected function fireLoginEvent($user, $remember = false)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->fire(new Events\Login($user, $remember));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the session with the given ID.
|
||||
*
|
||||
@@ -479,48 +433,22 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected function updateSession($id)
|
||||
{
|
||||
$this->session->set($this->getName(), $id);
|
||||
$this->session->put($this->getName(), $id);
|
||||
|
||||
$this->session->migrate(true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Log the given user ID into the application.
|
||||
* Create a new "remember me" token for the user if one doesn't already exist.
|
||||
*
|
||||
* @param mixed $id
|
||||
* @param bool $remember
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
public function loginUsingId($id, $remember = false)
|
||||
protected function ensureRememberTokenIsSet(AuthenticatableContract $user)
|
||||
{
|
||||
$user = $this->provider->retrieveById($id);
|
||||
|
||||
if (! is_null($user)) {
|
||||
$this->login($user, $remember);
|
||||
|
||||
return $user;
|
||||
if (empty($user->getRememberToken())) {
|
||||
$this->cycleRememberToken($user);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Log the given user ID into the application without sessions or cookies.
|
||||
*
|
||||
* @param mixed $id
|
||||
* @return bool
|
||||
*/
|
||||
public function onceUsingId($id)
|
||||
{
|
||||
$user = $this->provider->retrieveById($id);
|
||||
|
||||
if (! is_null($user)) {
|
||||
$this->setUser($user);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -531,9 +459,9 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
*/
|
||||
protected function queueRecallerCookie(AuthenticatableContract $user)
|
||||
{
|
||||
$value = $user->getAuthIdentifier().'|'.$user->getRememberToken();
|
||||
|
||||
$this->getCookieJar()->queue($this->createRecaller($value));
|
||||
$this->getCookieJar()->queue($this->createRecaller(
|
||||
$user->getAuthIdentifier().'|'.$user->getRememberToken().'|'.$user->getAuthPassword()
|
||||
));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -562,11 +490,11 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
$this->clearUserDataFromStorage();
|
||||
|
||||
if (! is_null($this->user)) {
|
||||
$this->refreshRememberToken($user);
|
||||
$this->cycleRememberToken($user);
|
||||
}
|
||||
|
||||
if (isset($this->events)) {
|
||||
$this->events->fire(new Events\Logout($user));
|
||||
$this->events->dispatch(new Events\Logout($user));
|
||||
}
|
||||
|
||||
// Once we have fired the logout event we will clear the users out of memory
|
||||
@@ -586,10 +514,9 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
{
|
||||
$this->session->remove($this->getName());
|
||||
|
||||
if (! is_null($this->getRecaller())) {
|
||||
$recaller = $this->getRecallerName();
|
||||
|
||||
$this->getCookieJar()->queue($this->getCookieJar()->forget($recaller));
|
||||
if (! is_null($this->recaller())) {
|
||||
$this->getCookieJar()->queue($this->getCookieJar()
|
||||
->forget($this->getRecallerName()));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -599,7 +526,7 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
protected function refreshRememberToken(AuthenticatableContract $user)
|
||||
protected function cycleRememberToken(AuthenticatableContract $user)
|
||||
{
|
||||
$user->setRememberToken($token = Str::random(60));
|
||||
|
||||
@@ -607,18 +534,115 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new "remember me" token for the user if one doesn't already exist.
|
||||
* Register an authentication attempt event listener.
|
||||
*
|
||||
* @param mixed $callback
|
||||
* @return void
|
||||
*/
|
||||
public function attempting($callback)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->listen(Events\Attempting::class, $callback);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire the attempt event with the arguments.
|
||||
*
|
||||
* @param array $credentials
|
||||
* @param bool $remember
|
||||
* @return void
|
||||
*/
|
||||
protected function fireAttemptEvent(array $credentials, $remember = false)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Attempting(
|
||||
$credentials, $remember
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire the login event if the dispatcher is set.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @param bool $remember
|
||||
* @return void
|
||||
*/
|
||||
protected function fireLoginEvent($user, $remember = false)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Login($user, $remember));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire the authenticated event if the dispatcher is set.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable $user
|
||||
* @return void
|
||||
*/
|
||||
protected function createRememberTokenIfDoesntExist(AuthenticatableContract $user)
|
||||
protected function fireAuthenticatedEvent($user)
|
||||
{
|
||||
if (empty($user->getRememberToken())) {
|
||||
$this->refreshRememberToken($user);
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Authenticated($user));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire the failed authentication attempt event with the given arguments.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Auth\Authenticatable|null $user
|
||||
* @param array $credentials
|
||||
* @return void
|
||||
*/
|
||||
protected function fireFailedEvent($user, array $credentials)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch(new Events\Failed($user, $credentials));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the last user we attempted to authenticate.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable
|
||||
*/
|
||||
public function getLastAttempted()
|
||||
{
|
||||
return $this->lastAttempted;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a unique identifier for the auth session value.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function getName()
|
||||
{
|
||||
return 'login_'.$this->name.'_'.sha1(static::class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the name of the cookie used to store the "recaller".
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function getRecallerName()
|
||||
{
|
||||
return 'remember_'.$this->name.'_'.sha1(static::class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the user was authenticated via "remember me" cookie.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function viaRemember()
|
||||
{
|
||||
return $this->viaRemember;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the cookie creator instance used by the guard.
|
||||
*
|
||||
@@ -670,34 +694,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.
|
||||
*
|
||||
@@ -720,6 +723,8 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
|
||||
$this->loggedOut = false;
|
||||
|
||||
$this->fireAuthenticatedEvent($user);
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
@@ -745,44 +750,4 @@ class SessionGuard implements StatefulGuard, SupportsBasicAuth
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the last user we attempted to authenticate.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Auth\Authenticatable
|
||||
*/
|
||||
public function getLastAttempted()
|
||||
{
|
||||
return $this->lastAttempted;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a unique identifier for the auth session value.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function getName()
|
||||
{
|
||||
return 'login_'.$this->name.'_'.sha1(static::class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the name of the cookie used to store the "recaller".
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function getRecallerName()
|
||||
{
|
||||
return 'remember_'.$this->name.'_'.sha1(static::class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the user was authenticated via "remember me" cookie.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function viaRemember()
|
||||
{
|
||||
return $this->viaRemember;
|
||||
}
|
||||
}
|
||||
|
@@ -18,7 +18,7 @@ class TokenGuard implements Guard
|
||||
protected $request;
|
||||
|
||||
/**
|
||||
* The name of the field on the request containing the API token.
|
||||
* The name of the query string item from the request containing the API token.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
@@ -78,9 +78,13 @@ class TokenGuard implements Guard
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
protected function getTokenForRequest()
|
||||
public function getTokenForRequest()
|
||||
{
|
||||
$token = $this->request->input($this->inputKey);
|
||||
$token = $this->request->query($this->inputKey);
|
||||
|
||||
if (empty($token)) {
|
||||
$token = $this->request->input($this->inputKey);
|
||||
}
|
||||
|
||||
if (empty($token)) {
|
||||
$token = $this->request->bearerToken();
|
||||
|
@@ -2,7 +2,7 @@
|
||||
"name": "illuminate/auth",
|
||||
"description": "The Illuminate Auth package.",
|
||||
"license": "MIT",
|
||||
"homepage": "http://laravel.com",
|
||||
"homepage": "https://laravel.com",
|
||||
"support": {
|
||||
"issues": "https://github.com/laravel/framework/issues",
|
||||
"source": "https://github.com/laravel/framework"
|
||||
@@ -14,11 +14,11 @@
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=5.5.9",
|
||||
"illuminate/contracts": "5.2.*",
|
||||
"illuminate/http": "5.2.*",
|
||||
"illuminate/support": "5.2.*",
|
||||
"nesbot/carbon": "~1.20"
|
||||
"php": ">=7.0",
|
||||
"illuminate/contracts": "5.5.*",
|
||||
"illuminate/http": "5.5.*",
|
||||
"illuminate/queue": "5.5.*",
|
||||
"illuminate/support": "5.5.*"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
@@ -27,13 +27,16 @@
|
||||
},
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "5.2-dev"
|
||||
"dev-master": "5.5-dev"
|
||||
}
|
||||
},
|
||||
"suggest": {
|
||||
"illuminate/console": "Required to use the auth:clear-resets command (5.2.*).",
|
||||
"illuminate/queue": "Required to fire login / logout events (5.2.*).",
|
||||
"illuminate/session": "Required to use the session based guard (5.2.*)."
|
||||
"illuminate/console": "Required to use the auth:clear-resets command (5.5.*).",
|
||||
"illuminate/queue": "Required to fire login / logout events (5.5.*).",
|
||||
"illuminate/session": "Required to use the session based guard (5.5.*)."
|
||||
},
|
||||
"config": {
|
||||
"sort-packages": true
|
||||
},
|
||||
"minimum-stability": "dev"
|
||||
}
|
||||
|
21
vendor/laravel/framework/src/Illuminate/Broadcasting/BroadcastController.php
vendored
Normal file
21
vendor/laravel/framework/src/Illuminate/Broadcasting/BroadcastController.php
vendored
Normal file
@@ -0,0 +1,21 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Routing\Controller;
|
||||
use Illuminate\Support\Facades\Broadcast;
|
||||
|
||||
class BroadcastController extends Controller
|
||||
{
|
||||
/**
|
||||
* Authenticate the request for channel access.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function authenticate(Request $request)
|
||||
{
|
||||
return Broadcast::auth($request);
|
||||
}
|
||||
}
|
@@ -4,49 +4,49 @@ namespace Illuminate\Broadcasting;
|
||||
|
||||
use ReflectionClass;
|
||||
use ReflectionProperty;
|
||||
use Illuminate\Contracts\Queue\Job;
|
||||
use Illuminate\Support\Arr;
|
||||
use Illuminate\Bus\Queueable;
|
||||
use Illuminate\Contracts\Queue\ShouldQueue;
|
||||
use Illuminate\Contracts\Support\Arrayable;
|
||||
use Illuminate\Contracts\Broadcasting\Broadcaster;
|
||||
|
||||
class BroadcastEvent
|
||||
class BroadcastEvent implements ShouldQueue
|
||||
{
|
||||
use Queueable;
|
||||
|
||||
/**
|
||||
* The broadcaster implementation.
|
||||
* The event instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Broadcasting\Broadcaster
|
||||
* @var mixed
|
||||
*/
|
||||
protected $broadcaster;
|
||||
public $event;
|
||||
|
||||
/**
|
||||
* Create a new job handler instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Broadcasting\Broadcaster $broadcaster
|
||||
* @param mixed $event
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Broadcaster $broadcaster)
|
||||
public function __construct($event)
|
||||
{
|
||||
$this->broadcaster = $broadcaster;
|
||||
$this->event = $event;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle the queued job.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Queue\Job $job
|
||||
* @param array $data
|
||||
* @param \Illuminate\Contracts\Broadcasting\Broadcaster $broadcaster
|
||||
* @return void
|
||||
*/
|
||||
public function fire(Job $job, array $data)
|
||||
public function handle(Broadcaster $broadcaster)
|
||||
{
|
||||
$event = unserialize($data['event']);
|
||||
$name = method_exists($this->event, 'broadcastAs')
|
||||
? $this->event->broadcastAs() : get_class($this->event);
|
||||
|
||||
$name = method_exists($event, 'broadcastAs')
|
||||
? $event->broadcastAs() : get_class($event);
|
||||
|
||||
$this->broadcaster->broadcast(
|
||||
$event->broadcastOn(), $name, $this->getPayloadFromEvent($event)
|
||||
$broadcaster->broadcast(
|
||||
Arr::wrap($this->event->broadcastOn()), $name,
|
||||
$this->getPayloadFromEvent($this->event)
|
||||
);
|
||||
|
||||
$job->delete();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -58,7 +58,9 @@ class BroadcastEvent
|
||||
protected function getPayloadFromEvent($event)
|
||||
{
|
||||
if (method_exists($event, 'broadcastWith')) {
|
||||
return $event->broadcastWith();
|
||||
return array_merge(
|
||||
$event->broadcastWith(), ['socket' => data_get($event, 'socket')]
|
||||
);
|
||||
}
|
||||
|
||||
$payload = [];
|
||||
@@ -67,6 +69,8 @@ class BroadcastEvent
|
||||
$payload[$property->getName()] = $this->formatProperty($property->getValue($event));
|
||||
}
|
||||
|
||||
unset($payload['broadcastQueue']);
|
||||
|
||||
return $payload;
|
||||
}
|
||||
|
||||
@@ -84,4 +88,24 @@ class BroadcastEvent
|
||||
|
||||
return $value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the display name for the queued job.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function displayName()
|
||||
{
|
||||
return get_class($this->event);
|
||||
}
|
||||
|
||||
/**
|
||||
* Prepare the instance for cloning.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __clone()
|
||||
{
|
||||
$this->event = clone $this->event;
|
||||
}
|
||||
}
|
||||
|
10
vendor/laravel/framework/src/Illuminate/Broadcasting/BroadcastException.php
vendored
Normal file
10
vendor/laravel/framework/src/Illuminate/Broadcasting/BroadcastException.php
vendored
Normal file
@@ -0,0 +1,10 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
use RuntimeException;
|
||||
|
||||
class BroadcastException extends RuntimeException
|
||||
{
|
||||
//
|
||||
}
|
@@ -2,15 +2,20 @@
|
||||
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
use Pusher;
|
||||
use Closure;
|
||||
use Illuminate\Support\Arr;
|
||||
use Pusher\Pusher;
|
||||
use Psr\Log\LoggerInterface;
|
||||
use InvalidArgumentException;
|
||||
use Illuminate\Broadcasting\Broadcasters\LogBroadcaster;
|
||||
use Illuminate\Broadcasting\Broadcasters\NullBroadcaster;
|
||||
use Illuminate\Contracts\Broadcasting\ShouldBroadcastNow;
|
||||
use Illuminate\Broadcasting\Broadcasters\RedisBroadcaster;
|
||||
use Illuminate\Broadcasting\Broadcasters\PusherBroadcaster;
|
||||
use Illuminate\Contracts\Broadcasting\Factory as FactoryContract;
|
||||
|
||||
/**
|
||||
* @mixin \Illuminate\Contracts\Broadcasting\Broadcaster
|
||||
*/
|
||||
class BroadcastManager implements FactoryContract
|
||||
{
|
||||
/**
|
||||
@@ -45,6 +50,82 @@ class BroadcastManager implements FactoryContract
|
||||
$this->app = $app;
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the routes for handling broadcast authentication and sockets.
|
||||
*
|
||||
* @param array|null $attributes
|
||||
* @return void
|
||||
*/
|
||||
public function routes(array $attributes = null)
|
||||
{
|
||||
if ($this->app->routesAreCached()) {
|
||||
return;
|
||||
}
|
||||
|
||||
$attributes = $attributes ?: ['middleware' => ['web']];
|
||||
|
||||
$this->app['router']->group($attributes, function ($router) {
|
||||
$router->post('/broadcasting/auth', '\\'.BroadcastController::class.'@authenticate');
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the socket ID for the given request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request|null $request
|
||||
* @return string|null
|
||||
*/
|
||||
public function socket($request = null)
|
||||
{
|
||||
if (! $request && ! $this->app->bound('request')) {
|
||||
return;
|
||||
}
|
||||
|
||||
$request = $request ?: $this->app['request'];
|
||||
|
||||
return $request->header('X-Socket-ID');
|
||||
}
|
||||
|
||||
/**
|
||||
* Begin broadcasting an event.
|
||||
*
|
||||
* @param mixed|null $event
|
||||
* @return \Illuminate\Broadcasting\PendingBroadcast|void
|
||||
*/
|
||||
public function event($event = null)
|
||||
{
|
||||
return new PendingBroadcast($this->app->make('events'), $event);
|
||||
}
|
||||
|
||||
/**
|
||||
* Queue the given event for broadcast.
|
||||
*
|
||||
* @param mixed $event
|
||||
* @return void
|
||||
*/
|
||||
public function queue($event)
|
||||
{
|
||||
$connection = $event instanceof ShouldBroadcastNow ? 'sync' : null;
|
||||
|
||||
if (is_null($connection) && isset($event->connection)) {
|
||||
$connection = $event->connection;
|
||||
}
|
||||
|
||||
$queue = null;
|
||||
|
||||
if (method_exists($event, 'broadcastQueue')) {
|
||||
$queue = $event->broadcastQueue();
|
||||
} elseif (isset($event->broadcastQueue)) {
|
||||
$queue = $event->broadcastQueue;
|
||||
} elseif (isset($event->queue)) {
|
||||
$queue = $event->queue;
|
||||
}
|
||||
|
||||
$this->app->make('queue')->connection($connection)->pushOn(
|
||||
$queue, new BroadcastEvent(clone $event)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a driver instance.
|
||||
*
|
||||
@@ -77,7 +158,7 @@ class BroadcastManager implements FactoryContract
|
||||
*/
|
||||
protected function get($name)
|
||||
{
|
||||
return isset($this->drivers[$name]) ? $this->drivers[$name] : $this->resolve($name);
|
||||
return $this->drivers[$name] ?? $this->resolve($name);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -98,15 +179,15 @@ class BroadcastManager implements FactoryContract
|
||||
|
||||
if (isset($this->customCreators[$config['driver']])) {
|
||||
return $this->callCustomCreator($config);
|
||||
} else {
|
||||
$driverMethod = 'create'.ucfirst($config['driver']).'Driver';
|
||||
|
||||
if (method_exists($this, $driverMethod)) {
|
||||
return $this->{$driverMethod}($config);
|
||||
} else {
|
||||
throw new InvalidArgumentException("Driver [{$config['driver']}] is not supported.");
|
||||
}
|
||||
}
|
||||
|
||||
$driverMethod = 'create'.ucfirst($config['driver']).'Driver';
|
||||
|
||||
if (! method_exists($this, $driverMethod)) {
|
||||
throw new InvalidArgumentException("Driver [{$config['driver']}] is not supported.");
|
||||
}
|
||||
|
||||
return $this->{$driverMethod}($config);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -129,7 +210,8 @@ class BroadcastManager implements FactoryContract
|
||||
protected function createPusherDriver(array $config)
|
||||
{
|
||||
return new PusherBroadcaster(
|
||||
new Pusher($config['key'], $config['secret'], $config['app_id'], Arr::get($config, 'options', []))
|
||||
new Pusher($config['key'], $config['secret'],
|
||||
$config['app_id'], $config['options'] ?? [])
|
||||
);
|
||||
}
|
||||
|
||||
@@ -142,7 +224,7 @@ class BroadcastManager implements FactoryContract
|
||||
protected function createRedisDriver(array $config)
|
||||
{
|
||||
return new RedisBroadcaster(
|
||||
$this->app->make('redis'), Arr::get($config, 'connection')
|
||||
$this->app->make('redis'), $config['connection'] ?? null
|
||||
);
|
||||
}
|
||||
|
||||
@@ -155,10 +237,21 @@ class BroadcastManager implements FactoryContract
|
||||
protected function createLogDriver(array $config)
|
||||
{
|
||||
return new LogBroadcaster(
|
||||
$this->app->make('Psr\Log\LoggerInterface')
|
||||
$this->app->make(LoggerInterface::class)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create an instance of the driver.
|
||||
*
|
||||
* @param array $config
|
||||
* @return \Illuminate\Contracts\Broadcasting\Broadcaster
|
||||
*/
|
||||
protected function createNullDriver(array $config)
|
||||
{
|
||||
return new NullBroadcaster;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the connection configuration.
|
||||
*
|
||||
@@ -214,6 +307,6 @@ class BroadcastManager implements FactoryContract
|
||||
*/
|
||||
public function __call($method, $parameters)
|
||||
{
|
||||
return call_user_func_array([$this->driver(), $method], $parameters);
|
||||
return $this->driver()->$method(...$parameters);
|
||||
}
|
||||
}
|
||||
|
@@ -3,6 +3,8 @@
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Contracts\Broadcasting\Factory as BroadcastingFactory;
|
||||
use Illuminate\Contracts\Broadcasting\Broadcaster as BroadcasterContract;
|
||||
|
||||
class BroadcastServiceProvider extends ServiceProvider
|
||||
{
|
||||
@@ -20,16 +22,16 @@ class BroadcastServiceProvider extends ServiceProvider
|
||||
*/
|
||||
public function register()
|
||||
{
|
||||
$this->app->singleton('Illuminate\Broadcasting\BroadcastManager', function ($app) {
|
||||
$this->app->singleton(BroadcastManager::class, function ($app) {
|
||||
return new BroadcastManager($app);
|
||||
});
|
||||
|
||||
$this->app->singleton('Illuminate\Contracts\Broadcasting\Broadcaster', function ($app) {
|
||||
return $app->make('Illuminate\Broadcasting\BroadcastManager')->connection();
|
||||
$this->app->singleton(BroadcasterContract::class, function ($app) {
|
||||
return $app->make(BroadcastManager::class)->connection();
|
||||
});
|
||||
|
||||
$this->app->alias(
|
||||
'Illuminate\Broadcasting\BroadcastManager', 'Illuminate\Contracts\Broadcasting\Factory'
|
||||
BroadcastManager::class, BroadcastingFactory::class
|
||||
);
|
||||
}
|
||||
|
||||
@@ -41,9 +43,9 @@ class BroadcastServiceProvider extends ServiceProvider
|
||||
public function provides()
|
||||
{
|
||||
return [
|
||||
'Illuminate\Broadcasting\BroadcastManager',
|
||||
'Illuminate\Contracts\Broadcasting\Factory',
|
||||
'Illuminate\Contracts\Broadcasting\Broadcaster',
|
||||
BroadcastManager::class,
|
||||
BroadcastingFactory::class,
|
||||
BroadcasterContract::class,
|
||||
];
|
||||
}
|
||||
}
|
||||
|
204
vendor/laravel/framework/src/Illuminate/Broadcasting/Broadcasters/Broadcaster.php
vendored
Normal file
204
vendor/laravel/framework/src/Illuminate/Broadcasting/Broadcasters/Broadcaster.php
vendored
Normal file
@@ -0,0 +1,204 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting\Broadcasters;
|
||||
|
||||
use ReflectionFunction;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Container\Container;
|
||||
use Illuminate\Contracts\Routing\UrlRoutable;
|
||||
use Illuminate\Contracts\Routing\BindingRegistrar;
|
||||
use Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException;
|
||||
use Illuminate\Contracts\Broadcasting\Broadcaster as BroadcasterContract;
|
||||
|
||||
abstract class Broadcaster implements BroadcasterContract
|
||||
{
|
||||
/**
|
||||
* The registered channel authenticators.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $channels = [];
|
||||
|
||||
/**
|
||||
* The binding registrar instance.
|
||||
*
|
||||
* @var BindingRegistrar
|
||||
*/
|
||||
protected $bindingRegistrar;
|
||||
|
||||
/**
|
||||
* Register a channel authenticator.
|
||||
*
|
||||
* @param string $channel
|
||||
* @param callable $callback
|
||||
* @return $this
|
||||
*/
|
||||
public function channel($channel, callable $callback)
|
||||
{
|
||||
$this->channels[$channel] = $callback;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Authenticate the incoming request for a given channel.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param string $channel
|
||||
* @return mixed
|
||||
* @throws \Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException
|
||||
*/
|
||||
protected function verifyUserCanAccessChannel($request, $channel)
|
||||
{
|
||||
foreach ($this->channels as $pattern => $callback) {
|
||||
if (! Str::is(preg_replace('/\{(.*?)\}/', '*', $pattern), $channel)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$parameters = $this->extractAuthParameters($pattern, $channel, $callback);
|
||||
|
||||
if ($result = $callback($request->user(), ...$parameters)) {
|
||||
return $this->validAuthenticationResponse($request, $result);
|
||||
}
|
||||
}
|
||||
|
||||
throw new AccessDeniedHttpException;
|
||||
}
|
||||
|
||||
/**
|
||||
* Extract the parameters from the given pattern and channel.
|
||||
*
|
||||
* @param string $pattern
|
||||
* @param string $channel
|
||||
* @param callable $callback
|
||||
* @return array
|
||||
*/
|
||||
protected function extractAuthParameters($pattern, $channel, $callback)
|
||||
{
|
||||
$callbackParameters = (new ReflectionFunction($callback))->getParameters();
|
||||
|
||||
return collect($this->extractChannelKeys($pattern, $channel))->reject(function ($value, $key) {
|
||||
return is_numeric($key);
|
||||
})->map(function ($value, $key) use ($callbackParameters) {
|
||||
return $this->resolveBinding($key, $value, $callbackParameters);
|
||||
})->values()->all();
|
||||
}
|
||||
|
||||
/**
|
||||
* Extract the channel keys from the incoming channel name.
|
||||
*
|
||||
* @param string $pattern
|
||||
* @param string $channel
|
||||
* @return array
|
||||
*/
|
||||
protected function extractChannelKeys($pattern, $channel)
|
||||
{
|
||||
preg_match('/^'.preg_replace('/\{(.*?)\}/', '(?<$1>[^\.]+)', $pattern).'/', $channel, $keys);
|
||||
|
||||
return $keys;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve the given parameter binding.
|
||||
*
|
||||
* @param string $key
|
||||
* @param string $value
|
||||
* @param array $callbackParameters
|
||||
* @return mixed
|
||||
*/
|
||||
protected function resolveBinding($key, $value, $callbackParameters)
|
||||
{
|
||||
$newValue = $this->resolveExplicitBindingIfPossible($key, $value);
|
||||
|
||||
return $newValue === $value ? $this->resolveImplicitBindingIfPossible(
|
||||
$key, $value, $callbackParameters
|
||||
) : $newValue;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve an explicit parameter binding if applicable.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @return mixed
|
||||
*/
|
||||
protected function resolveExplicitBindingIfPossible($key, $value)
|
||||
{
|
||||
$binder = $this->binder();
|
||||
|
||||
if ($binder && $binder->getBindingCallback($key)) {
|
||||
return call_user_func($binder->getBindingCallback($key), $value);
|
||||
}
|
||||
|
||||
return $value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve an implicit parameter binding if applicable.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param array $callbackParameters
|
||||
* @return mixed
|
||||
* @throws \Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException
|
||||
*/
|
||||
protected function resolveImplicitBindingIfPossible($key, $value, $callbackParameters)
|
||||
{
|
||||
foreach ($callbackParameters as $parameter) {
|
||||
if (! $this->isImplicitlyBindable($key, $parameter)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$instance = $parameter->getClass()->newInstance();
|
||||
|
||||
if (! $model = $instance->resolveRouteBinding($value)) {
|
||||
throw new AccessDeniedHttpException;
|
||||
}
|
||||
|
||||
return $model;
|
||||
}
|
||||
|
||||
return $value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if a given key and parameter is implicitly bindable.
|
||||
*
|
||||
* @param string $key
|
||||
* @param \ReflectionParameter $parameter
|
||||
* @return bool
|
||||
*/
|
||||
protected function isImplicitlyBindable($key, $parameter)
|
||||
{
|
||||
return $parameter->name === $key && $parameter->getClass() &&
|
||||
$parameter->getClass()->isSubclassOf(UrlRoutable::class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Format the channel array into an array of strings.
|
||||
*
|
||||
* @param array $channels
|
||||
* @return array
|
||||
*/
|
||||
protected function formatChannels(array $channels)
|
||||
{
|
||||
return array_map(function ($channel) {
|
||||
return (string) $channel;
|
||||
}, $channels);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the model binding registrar instance.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Routing\BindingRegistrar
|
||||
*/
|
||||
protected function binder()
|
||||
{
|
||||
if (! $this->bindingRegistrar) {
|
||||
$this->bindingRegistrar = Container::getInstance()->bound(BindingRegistrar::class)
|
||||
? Container::getInstance()->make(BindingRegistrar::class) : null;
|
||||
}
|
||||
|
||||
return $this->bindingRegistrar;
|
||||
}
|
||||
}
|
@@ -3,9 +3,8 @@
|
||||
namespace Illuminate\Broadcasting\Broadcasters;
|
||||
|
||||
use Psr\Log\LoggerInterface;
|
||||
use Illuminate\Contracts\Broadcasting\Broadcaster;
|
||||
|
||||
class LogBroadcaster implements Broadcaster
|
||||
class LogBroadcaster extends Broadcaster
|
||||
{
|
||||
/**
|
||||
* The logger implementation.
|
||||
@@ -25,12 +24,28 @@ class LogBroadcaster implements Broadcaster
|
||||
$this->logger = $logger;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function auth($request)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function validAuthenticationResponse($request, $result)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function broadcast(array $channels, $event, array $payload = [])
|
||||
{
|
||||
$channels = implode(', ', $channels);
|
||||
$channels = implode(', ', $this->formatChannels($channels));
|
||||
|
||||
$payload = json_encode($payload, JSON_PRETTY_PRINT);
|
||||
|
||||
|
30
vendor/laravel/framework/src/Illuminate/Broadcasting/Broadcasters/NullBroadcaster.php
vendored
Normal file
30
vendor/laravel/framework/src/Illuminate/Broadcasting/Broadcasters/NullBroadcaster.php
vendored
Normal file
@@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting\Broadcasters;
|
||||
|
||||
class NullBroadcaster extends Broadcaster
|
||||
{
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function auth($request)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function validAuthenticationResponse($request, $result)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function broadcast(array $channels, $event, array $payload = [])
|
||||
{
|
||||
//
|
||||
}
|
||||
}
|
@@ -2,22 +2,25 @@
|
||||
|
||||
namespace Illuminate\Broadcasting\Broadcasters;
|
||||
|
||||
use Pusher;
|
||||
use Illuminate\Contracts\Broadcasting\Broadcaster;
|
||||
use Pusher\Pusher;
|
||||
use Illuminate\Support\Arr;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Broadcasting\BroadcastException;
|
||||
use Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException;
|
||||
|
||||
class PusherBroadcaster implements Broadcaster
|
||||
class PusherBroadcaster extends Broadcaster
|
||||
{
|
||||
/**
|
||||
* The Pusher SDK instance.
|
||||
*
|
||||
* @var \Pusher
|
||||
* @var \Pusher\Pusher
|
||||
*/
|
||||
protected $pusher;
|
||||
|
||||
/**
|
||||
* Create a new broadcaster instance.
|
||||
*
|
||||
* @param \Pusher $pusher
|
||||
* @param \Pusher\Pusher $pusher
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Pusher $pusher)
|
||||
@@ -26,17 +29,90 @@ class PusherBroadcaster implements Broadcaster
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
* Authenticate the incoming request for a given channel.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return mixed
|
||||
* @throws \Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException
|
||||
*/
|
||||
public function auth($request)
|
||||
{
|
||||
if (Str::startsWith($request->channel_name, ['private-', 'presence-']) &&
|
||||
! $request->user()) {
|
||||
throw new AccessDeniedHttpException;
|
||||
}
|
||||
|
||||
$channelName = Str::startsWith($request->channel_name, 'private-')
|
||||
? Str::replaceFirst('private-', '', $request->channel_name)
|
||||
: Str::replaceFirst('presence-', '', $request->channel_name);
|
||||
|
||||
return parent::verifyUserCanAccessChannel(
|
||||
$request, $channelName
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the valid authentication response.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param mixed $result
|
||||
* @return mixed
|
||||
*/
|
||||
public function validAuthenticationResponse($request, $result)
|
||||
{
|
||||
if (Str::startsWith($request->channel_name, 'private')) {
|
||||
return $this->decodePusherResponse(
|
||||
$this->pusher->socket_auth($request->channel_name, $request->socket_id)
|
||||
);
|
||||
}
|
||||
|
||||
return $this->decodePusherResponse(
|
||||
$this->pusher->presence_auth(
|
||||
$request->channel_name, $request->socket_id, $request->user()->getAuthIdentifier(), $result)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Decode the given Pusher response.
|
||||
*
|
||||
* @param mixed $response
|
||||
* @return array
|
||||
*/
|
||||
protected function decodePusherResponse($response)
|
||||
{
|
||||
return json_decode($response, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Broadcast the given event.
|
||||
*
|
||||
* @param array $channels
|
||||
* @param string $event
|
||||
* @param array $payload
|
||||
* @return void
|
||||
*/
|
||||
public function broadcast(array $channels, $event, array $payload = [])
|
||||
{
|
||||
$this->pusher->trigger($channels, $event, $payload);
|
||||
$socket = Arr::pull($payload, 'socket');
|
||||
|
||||
$response = $this->pusher->trigger(
|
||||
$this->formatChannels($channels), $event, $payload, $socket, true
|
||||
);
|
||||
|
||||
if ((is_array($response) && $response['status'] >= 200 && $response['status'] <= 299)
|
||||
|| $response === true) {
|
||||
return;
|
||||
}
|
||||
|
||||
throw new BroadcastException(
|
||||
is_bool($response) ? 'Failed to connect to Pusher.' : $response['body']
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the Pusher SDK instance.
|
||||
*
|
||||
* @return \Pusher
|
||||
* @return \Pusher\Pusher
|
||||
*/
|
||||
public function getPusher()
|
||||
{
|
||||
|
@@ -2,15 +2,17 @@
|
||||
|
||||
namespace Illuminate\Broadcasting\Broadcasters;
|
||||
|
||||
use Illuminate\Contracts\Broadcasting\Broadcaster;
|
||||
use Illuminate\Contracts\Redis\Database as RedisDatabase;
|
||||
use Illuminate\Support\Arr;
|
||||
use Illuminate\Support\Str;
|
||||
use Illuminate\Contracts\Redis\Factory as Redis;
|
||||
use Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException;
|
||||
|
||||
class RedisBroadcaster implements Broadcaster
|
||||
class RedisBroadcaster extends Broadcaster
|
||||
{
|
||||
/**
|
||||
* The Redis instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Redis\Database
|
||||
* @var \Illuminate\Contracts\Redis\Factory
|
||||
*/
|
||||
protected $redis;
|
||||
|
||||
@@ -24,26 +26,77 @@ class RedisBroadcaster implements Broadcaster
|
||||
/**
|
||||
* Create a new broadcaster instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Redis\Database $redis
|
||||
* @param \Illuminate\Contracts\Redis\Factory $redis
|
||||
* @param string $connection
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(RedisDatabase $redis, $connection = null)
|
||||
public function __construct(Redis $redis, $connection = null)
|
||||
{
|
||||
$this->redis = $redis;
|
||||
$this->connection = $connection;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
* Authenticate the incoming request for a given channel.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return mixed
|
||||
* @throws \Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException
|
||||
*/
|
||||
public function auth($request)
|
||||
{
|
||||
if (Str::startsWith($request->channel_name, ['private-', 'presence-']) &&
|
||||
! $request->user()) {
|
||||
throw new AccessDeniedHttpException;
|
||||
}
|
||||
|
||||
$channelName = Str::startsWith($request->channel_name, 'private-')
|
||||
? Str::replaceFirst('private-', '', $request->channel_name)
|
||||
: Str::replaceFirst('presence-', '', $request->channel_name);
|
||||
|
||||
return parent::verifyUserCanAccessChannel(
|
||||
$request, $channelName
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the valid authentication response.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param mixed $result
|
||||
* @return mixed
|
||||
*/
|
||||
public function validAuthenticationResponse($request, $result)
|
||||
{
|
||||
if (is_bool($result)) {
|
||||
return json_encode($result);
|
||||
}
|
||||
|
||||
return json_encode(['channel_data' => [
|
||||
'user_id' => $request->user()->getAuthIdentifier(),
|
||||
'user_info' => $result,
|
||||
]]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Broadcast the given event.
|
||||
*
|
||||
* @param array $channels
|
||||
* @param string $event
|
||||
* @param array $payload
|
||||
* @return void
|
||||
*/
|
||||
public function broadcast(array $channels, $event, array $payload = [])
|
||||
{
|
||||
$connection = $this->redis->connection($this->connection);
|
||||
|
||||
$payload = json_encode(['event' => $event, 'data' => $payload]);
|
||||
$payload = json_encode([
|
||||
'event' => $event,
|
||||
'data' => $payload,
|
||||
'socket' => Arr::pull($payload, 'socket'),
|
||||
]);
|
||||
|
||||
foreach ($channels as $channel) {
|
||||
foreach ($this->formatChannels($channels) as $channel) {
|
||||
$connection->publish($channel, $payload);
|
||||
}
|
||||
}
|
||||
|
34
vendor/laravel/framework/src/Illuminate/Broadcasting/Channel.php
vendored
Normal file
34
vendor/laravel/framework/src/Illuminate/Broadcasting/Channel.php
vendored
Normal file
@@ -0,0 +1,34 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
class Channel
|
||||
{
|
||||
/**
|
||||
* The channel's name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $name;
|
||||
|
||||
/**
|
||||
* Create a new channel instance.
|
||||
*
|
||||
* @param string $name
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($name)
|
||||
{
|
||||
$this->name = $name;
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert the channel instance to a string.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public function __toString()
|
||||
{
|
||||
return $this->name;
|
||||
}
|
||||
}
|
39
vendor/laravel/framework/src/Illuminate/Broadcasting/InteractsWithSockets.php
vendored
Normal file
39
vendor/laravel/framework/src/Illuminate/Broadcasting/InteractsWithSockets.php
vendored
Normal file
@@ -0,0 +1,39 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
use Illuminate\Support\Facades\Broadcast;
|
||||
|
||||
trait InteractsWithSockets
|
||||
{
|
||||
/**
|
||||
* The socket ID for the user that raised the event.
|
||||
*
|
||||
* @var string|null
|
||||
*/
|
||||
public $socket;
|
||||
|
||||
/**
|
||||
* Exclude the current user from receiving the broadcast.
|
||||
*
|
||||
* @return $this
|
||||
*/
|
||||
public function dontBroadcastToCurrentUser()
|
||||
{
|
||||
$this->socket = Broadcast::socket();
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Broadcast the event to everyone.
|
||||
*
|
||||
* @return $this
|
||||
*/
|
||||
public function broadcastToEveryone()
|
||||
{
|
||||
$this->socket = null;
|
||||
|
||||
return $this;
|
||||
}
|
||||
}
|
59
vendor/laravel/framework/src/Illuminate/Broadcasting/PendingBroadcast.php
vendored
Normal file
59
vendor/laravel/framework/src/Illuminate/Broadcasting/PendingBroadcast.php
vendored
Normal file
@@ -0,0 +1,59 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
|
||||
class PendingBroadcast
|
||||
{
|
||||
/**
|
||||
* The event dispatcher implementation.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Events\Dispatcher
|
||||
*/
|
||||
protected $events;
|
||||
|
||||
/**
|
||||
* The event instance.
|
||||
*
|
||||
* @var mixed
|
||||
*/
|
||||
protected $event;
|
||||
|
||||
/**
|
||||
* Create a new pending broadcast instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Events\Dispatcher $events
|
||||
* @param mixed $event
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Dispatcher $events, $event)
|
||||
{
|
||||
$this->event = $event;
|
||||
$this->events = $events;
|
||||
}
|
||||
|
||||
/**
|
||||
* Broadcast the event to everyone except the current user.
|
||||
*
|
||||
* @return $this
|
||||
*/
|
||||
public function toOthers()
|
||||
{
|
||||
if (method_exists($this->event, 'dontBroadcastToCurrentUser')) {
|
||||
$this->event->dontBroadcastToCurrentUser();
|
||||
}
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle the object's destruction.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __destruct()
|
||||
{
|
||||
$this->events->dispatch($this->event);
|
||||
}
|
||||
}
|
17
vendor/laravel/framework/src/Illuminate/Broadcasting/PresenceChannel.php
vendored
Normal file
17
vendor/laravel/framework/src/Illuminate/Broadcasting/PresenceChannel.php
vendored
Normal file
@@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
class PresenceChannel extends Channel
|
||||
{
|
||||
/**
|
||||
* Create a new channel instance.
|
||||
*
|
||||
* @param string $name
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($name)
|
||||
{
|
||||
parent::__construct('presence-'.$name);
|
||||
}
|
||||
}
|
17
vendor/laravel/framework/src/Illuminate/Broadcasting/PrivateChannel.php
vendored
Normal file
17
vendor/laravel/framework/src/Illuminate/Broadcasting/PrivateChannel.php
vendored
Normal file
@@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Broadcasting;
|
||||
|
||||
class PrivateChannel extends Channel
|
||||
{
|
||||
/**
|
||||
* Create a new channel instance.
|
||||
*
|
||||
* @param string $name
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($name)
|
||||
{
|
||||
parent::__construct('private-'.$name);
|
||||
}
|
||||
}
|
@@ -2,7 +2,7 @@
|
||||
"name": "illuminate/broadcasting",
|
||||
"description": "The Illuminate Broadcasting package.",
|
||||
"license": "MIT",
|
||||
"homepage": "http://laravel.com",
|
||||
"homepage": "https://laravel.com",
|
||||
"support": {
|
||||
"issues": "https://github.com/laravel/framework/issues",
|
||||
"source": "https://github.com/laravel/framework"
|
||||
@@ -14,9 +14,12 @@
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=5.5.9",
|
||||
"illuminate/contracts": "5.2.*",
|
||||
"illuminate/support": "5.2.*"
|
||||
"php": ">=7.0",
|
||||
"psr/log": "~1.0",
|
||||
"illuminate/bus": "5.5.*",
|
||||
"illuminate/contracts": "5.5.*",
|
||||
"illuminate/queue": "5.5.*",
|
||||
"illuminate/support": "5.5.*"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
@@ -25,11 +28,14 @@
|
||||
},
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "5.2-dev"
|
||||
"dev-master": "5.5-dev"
|
||||
}
|
||||
},
|
||||
"suggest": {
|
||||
"pusher/pusher-php-server": "Required to use the Pusher broadcast driver (~2.0)."
|
||||
"pusher/pusher-php-server": "Required to use the Pusher broadcast driver (~3.0)."
|
||||
},
|
||||
"config": {
|
||||
"sort-packages": true
|
||||
},
|
||||
"minimum-stability": "dev"
|
||||
}
|
||||
|
@@ -3,6 +3,9 @@
|
||||
namespace Illuminate\Bus;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Contracts\Bus\Dispatcher as DispatcherContract;
|
||||
use Illuminate\Contracts\Queue\Factory as QueueFactoryContract;
|
||||
use Illuminate\Contracts\Bus\QueueingDispatcher as QueueingDispatcherContract;
|
||||
|
||||
class BusServiceProvider extends ServiceProvider
|
||||
{
|
||||
@@ -20,18 +23,18 @@ class BusServiceProvider extends ServiceProvider
|
||||
*/
|
||||
public function register()
|
||||
{
|
||||
$this->app->singleton('Illuminate\Bus\Dispatcher', function ($app) {
|
||||
$this->app->singleton(Dispatcher::class, function ($app) {
|
||||
return new Dispatcher($app, function ($connection = null) use ($app) {
|
||||
return $app['Illuminate\Contracts\Queue\Factory']->connection($connection);
|
||||
return $app[QueueFactoryContract::class]->connection($connection);
|
||||
});
|
||||
});
|
||||
|
||||
$this->app->alias(
|
||||
'Illuminate\Bus\Dispatcher', 'Illuminate\Contracts\Bus\Dispatcher'
|
||||
Dispatcher::class, DispatcherContract::class
|
||||
);
|
||||
|
||||
$this->app->alias(
|
||||
'Illuminate\Bus\Dispatcher', 'Illuminate\Contracts\Bus\QueueingDispatcher'
|
||||
Dispatcher::class, QueueingDispatcherContract::class
|
||||
);
|
||||
}
|
||||
|
||||
@@ -43,9 +46,9 @@ class BusServiceProvider extends ServiceProvider
|
||||
public function provides()
|
||||
{
|
||||
return [
|
||||
'Illuminate\Bus\Dispatcher',
|
||||
'Illuminate\Contracts\Bus\Dispatcher',
|
||||
'Illuminate\Contracts\Bus\QueueingDispatcher',
|
||||
Dispatcher::class,
|
||||
DispatcherContract::class,
|
||||
QueueingDispatcherContract::class,
|
||||
];
|
||||
}
|
||||
}
|
||||
|
@@ -33,6 +33,13 @@ class Dispatcher implements QueueingDispatcher
|
||||
*/
|
||||
protected $pipes = [];
|
||||
|
||||
/**
|
||||
* The command to handler mapping for non-self-handling events.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $handlers = [];
|
||||
|
||||
/**
|
||||
* The queue resolver callback.
|
||||
*
|
||||
@@ -64,22 +71,57 @@ class Dispatcher implements QueueingDispatcher
|
||||
{
|
||||
if ($this->queueResolver && $this->commandShouldBeQueued($command)) {
|
||||
return $this->dispatchToQueue($command);
|
||||
} else {
|
||||
return $this->dispatchNow($command);
|
||||
}
|
||||
|
||||
return $this->dispatchNow($command);
|
||||
}
|
||||
|
||||
/**
|
||||
* Dispatch a command to its appropriate handler in the current process.
|
||||
*
|
||||
* @param mixed $command
|
||||
* @param mixed $handler
|
||||
* @return mixed
|
||||
*/
|
||||
public function dispatchNow($command)
|
||||
public function dispatchNow($command, $handler = null)
|
||||
{
|
||||
return $this->pipeline->send($command)->through($this->pipes)->then(function ($command) {
|
||||
return $this->container->call([$command, 'handle']);
|
||||
});
|
||||
if ($handler || $handler = $this->getCommandHandler($command)) {
|
||||
$callback = function ($command) use ($handler) {
|
||||
return $handler->handle($command);
|
||||
};
|
||||
} else {
|
||||
$callback = function ($command) {
|
||||
return $this->container->call([$command, 'handle']);
|
||||
};
|
||||
}
|
||||
|
||||
return $this->pipeline->send($command)->through($this->pipes)->then($callback);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the given command has a handler.
|
||||
*
|
||||
* @param mixed $command
|
||||
* @return bool
|
||||
*/
|
||||
public function hasCommandHandler($command)
|
||||
{
|
||||
return array_key_exists(get_class($command), $this->handlers);
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve the handler for a command.
|
||||
*
|
||||
* @param mixed $command
|
||||
* @return bool|mixed
|
||||
*/
|
||||
public function getCommandHandler($command)
|
||||
{
|
||||
if ($this->hasCommandHandler($command)) {
|
||||
return $this->container->make($this->handlers[get_class($command)]);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -103,7 +145,7 @@ class Dispatcher implements QueueingDispatcher
|
||||
*/
|
||||
public function dispatchToQueue($command)
|
||||
{
|
||||
$connection = isset($command->connection) ? $command->connection : null;
|
||||
$connection = $command->connection ?? null;
|
||||
|
||||
$queue = call_user_func($this->queueResolver, $connection);
|
||||
|
||||
@@ -113,9 +155,9 @@ class Dispatcher implements QueueingDispatcher
|
||||
|
||||
if (method_exists($command, 'queue')) {
|
||||
return $command->queue($queue, $command);
|
||||
} else {
|
||||
return $this->pushCommandToQueue($queue, $command);
|
||||
}
|
||||
|
||||
return $this->pushCommandToQueue($queue, $command);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -154,4 +196,17 @@ class Dispatcher implements QueueingDispatcher
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Map a command to a handler.
|
||||
*
|
||||
* @param array $map
|
||||
* @return $this
|
||||
*/
|
||||
public function map(array $map)
|
||||
{
|
||||
$this->handlers = array_merge($this->handlers, $map);
|
||||
|
||||
return $this;
|
||||
}
|
||||
}
|
||||
|
@@ -18,13 +18,34 @@ trait Queueable
|
||||
*/
|
||||
public $queue;
|
||||
|
||||
/**
|
||||
* The name of the connection the chain should be sent to.
|
||||
*
|
||||
* @var string|null
|
||||
*/
|
||||
public $chainConnection;
|
||||
|
||||
/**
|
||||
* The name of the queue the chain should be sent to.
|
||||
*
|
||||
* @var string|null
|
||||
*/
|
||||
public $chainQueue;
|
||||
|
||||
/**
|
||||
* The number of seconds before the job should be made available.
|
||||
*
|
||||
* @var \DateTime|int|null
|
||||
* @var \DateTimeInterface|\DateInterval|int|null
|
||||
*/
|
||||
public $delay;
|
||||
|
||||
/**
|
||||
* The jobs that should run if this job is successful.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
public $chained = [];
|
||||
|
||||
/**
|
||||
* Set the desired connection for the job.
|
||||
*
|
||||
@@ -51,10 +72,38 @@ trait Queueable
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the desired connection for the chain.
|
||||
*
|
||||
* @param string|null $connection
|
||||
* @return $this
|
||||
*/
|
||||
public function allOnConnection($connection)
|
||||
{
|
||||
$this->chainConnection = $connection;
|
||||
$this->connection = $connection;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the desired queue for the chain.
|
||||
*
|
||||
* @param string|null $queue
|
||||
* @return $this
|
||||
*/
|
||||
public function allOnQueue($queue)
|
||||
{
|
||||
$this->chainQueue = $queue;
|
||||
$this->queue = $queue;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the desired delay for the job.
|
||||
*
|
||||
* @param int|null $delay
|
||||
* @param \DateTimeInterface|\DateInterval|int|null $delay
|
||||
* @return $this
|
||||
*/
|
||||
public function delay($delay)
|
||||
@@ -63,4 +112,39 @@ trait Queueable
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the jobs that should run if this job is successful.
|
||||
*
|
||||
* @param array $chain
|
||||
* @return $this
|
||||
*/
|
||||
public function chain($chain)
|
||||
{
|
||||
$this->chained = collect($chain)->map(function ($job) {
|
||||
return serialize($job);
|
||||
})->all();
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Dispatch the next job on the chain.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function dispatchNextJobInChain()
|
||||
{
|
||||
if (! empty($this->chained)) {
|
||||
dispatch(tap(unserialize(array_shift($this->chained)), function ($next) {
|
||||
$next->chained = $this->chained;
|
||||
|
||||
$next->onConnection($next->connection ?: $this->chainConnection);
|
||||
$next->onQueue($next->queue ?: $this->chainQueue);
|
||||
|
||||
$next->chainConnection = $this->chainConnection;
|
||||
$next->chainQueue = $this->chainQueue;
|
||||
}));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -2,7 +2,7 @@
|
||||
"name": "illuminate/bus",
|
||||
"description": "The Illuminate Bus package.",
|
||||
"license": "MIT",
|
||||
"homepage": "http://laravel.com",
|
||||
"homepage": "https://laravel.com",
|
||||
"support": {
|
||||
"issues": "https://github.com/laravel/framework/issues",
|
||||
"source": "https://github.com/laravel/framework"
|
||||
@@ -14,10 +14,10 @@
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=5.5.9",
|
||||
"illuminate/contracts": "5.2.*",
|
||||
"illuminate/pipeline": "5.2.*",
|
||||
"illuminate/support": "5.2.*"
|
||||
"php": ">=7.0",
|
||||
"illuminate/contracts": "5.5.*",
|
||||
"illuminate/pipeline": "5.5.*",
|
||||
"illuminate/support": "5.5.*"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
@@ -26,8 +26,11 @@
|
||||
},
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "5.2-dev"
|
||||
"dev-master": "5.5-dev"
|
||||
}
|
||||
},
|
||||
"config": {
|
||||
"sort-packages": true
|
||||
},
|
||||
"minimum-stability": "dev"
|
||||
}
|
||||
|
@@ -55,12 +55,12 @@ class ApcStore extends TaggableStore implements Store
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes)
|
||||
{
|
||||
$this->apc->put($this->prefix.$key, $value, $minutes * 60);
|
||||
$this->apc->put($this->prefix.$key, $value, (int) ($minutes * 60));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -113,11 +113,11 @@ class ApcStore extends TaggableStore implements Store
|
||||
/**
|
||||
* Remove all items from the cache.
|
||||
*
|
||||
* @return void
|
||||
* @return bool
|
||||
*/
|
||||
public function flush()
|
||||
{
|
||||
$this->apc->flush();
|
||||
return $this->apc->flush();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@@ -83,10 +83,10 @@ class ApcWrapper
|
||||
/**
|
||||
* Remove all items from the cache.
|
||||
*
|
||||
* @return void
|
||||
* @return bool
|
||||
*/
|
||||
public function flush()
|
||||
{
|
||||
$this->apcu ? apcu_clear_cache() : apc_clear_cache('user');
|
||||
return $this->apcu ? apcu_clear_cache() : apc_clear_cache('user');
|
||||
}
|
||||
}
|
||||
|
@@ -33,7 +33,7 @@ class ArrayStore extends TaggableStore implements Store
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes)
|
||||
@@ -50,7 +50,8 @@ class ArrayStore extends TaggableStore implements Store
|
||||
*/
|
||||
public function increment($key, $value = 1)
|
||||
{
|
||||
$this->storage[$key] = ((int) $this->storage[$key]) + $value;
|
||||
$this->storage[$key] = ! isset($this->storage[$key])
|
||||
? $value : ((int) $this->storage[$key]) + $value;
|
||||
|
||||
return $this->storage[$key];
|
||||
}
|
||||
@@ -95,11 +96,13 @@ class ArrayStore extends TaggableStore implements Store
|
||||
/**
|
||||
* Remove all items from the cache.
|
||||
*
|
||||
* @return void
|
||||
* @return bool
|
||||
*/
|
||||
public function flush()
|
||||
{
|
||||
$this->storage = [];
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@@ -3,11 +3,14 @@
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Support\Arr;
|
||||
use InvalidArgumentException;
|
||||
use Illuminate\Contracts\Cache\Store;
|
||||
use Illuminate\Contracts\Cache\Factory as FactoryContract;
|
||||
use Illuminate\Contracts\Events\Dispatcher as DispatcherContract;
|
||||
|
||||
/**
|
||||
* @mixin \Illuminate\Contracts\Cache\Repository
|
||||
*/
|
||||
class CacheManager implements FactoryContract
|
||||
{
|
||||
/**
|
||||
@@ -46,7 +49,7 @@ class CacheManager implements FactoryContract
|
||||
* Get a cache store instance by name.
|
||||
*
|
||||
* @param string|null $name
|
||||
* @return mixed
|
||||
* @return \Illuminate\Contracts\Cache\Repository
|
||||
*/
|
||||
public function store($name = null)
|
||||
{
|
||||
@@ -74,7 +77,7 @@ class CacheManager implements FactoryContract
|
||||
*/
|
||||
protected function get($name)
|
||||
{
|
||||
return isset($this->stores[$name]) ? $this->stores[$name] : $this->resolve($name);
|
||||
return $this->stores[$name] ?? $this->resolve($name);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -161,7 +164,12 @@ class CacheManager implements FactoryContract
|
||||
{
|
||||
$prefix = $this->getPrefix($config);
|
||||
|
||||
$memcached = $this->app['memcached.connector']->connect($config['servers']);
|
||||
$memcached = $this->app['memcached.connector']->connect(
|
||||
$config['servers'],
|
||||
$config['persistent_id'] ?? null,
|
||||
$config['options'] ?? [],
|
||||
array_filter($config['sasl'] ?? [])
|
||||
);
|
||||
|
||||
return $this->repository(new MemcachedStore($memcached, $prefix));
|
||||
}
|
||||
@@ -186,7 +194,7 @@ class CacheManager implements FactoryContract
|
||||
{
|
||||
$redis = $this->app['redis'];
|
||||
|
||||
$connection = Arr::get($config, 'connection', 'default');
|
||||
$connection = $config['connection'] ?? 'default';
|
||||
|
||||
return $this->repository(new RedisStore($redis, $this->getPrefix($config), $connection));
|
||||
}
|
||||
@@ -199,11 +207,11 @@ class CacheManager implements FactoryContract
|
||||
*/
|
||||
protected function createDatabaseDriver(array $config)
|
||||
{
|
||||
$connection = $this->app['db']->connection(Arr::get($config, 'connection'));
|
||||
$connection = $this->app['db']->connection($config['connection'] ?? null);
|
||||
|
||||
return $this->repository(
|
||||
new DatabaseStore(
|
||||
$connection, $this->app['encrypter'], $config['table'], $this->getPrefix($config)
|
||||
$connection, $config['table'], $this->getPrefix($config)
|
||||
)
|
||||
);
|
||||
}
|
||||
@@ -218,9 +226,9 @@ class CacheManager implements FactoryContract
|
||||
{
|
||||
$repository = new Repository($store);
|
||||
|
||||
if ($this->app->bound('Illuminate\Contracts\Events\Dispatcher')) {
|
||||
if ($this->app->bound(DispatcherContract::class)) {
|
||||
$repository->setEventDispatcher(
|
||||
$this->app['Illuminate\Contracts\Events\Dispatcher']
|
||||
$this->app[DispatcherContract::class]
|
||||
);
|
||||
}
|
||||
|
||||
@@ -235,7 +243,7 @@ class CacheManager implements FactoryContract
|
||||
*/
|
||||
protected function getPrefix(array $config)
|
||||
{
|
||||
return Arr::get($config, 'prefix') ?: $this->app['config']['cache.prefix'];
|
||||
return $config['prefix'] ?? $this->app['config']['cache.prefix'];
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -279,7 +287,7 @@ class CacheManager implements FactoryContract
|
||||
*/
|
||||
public function extend($driver, Closure $callback)
|
||||
{
|
||||
$this->customCreators[$driver] = $callback;
|
||||
$this->customCreators[$driver] = $callback->bindTo($this, $this);
|
||||
|
||||
return $this;
|
||||
}
|
||||
@@ -293,6 +301,6 @@ class CacheManager implements FactoryContract
|
||||
*/
|
||||
public function __call($method, $parameters)
|
||||
{
|
||||
return call_user_func_array([$this->store(), $method], $parameters);
|
||||
return $this->store()->$method(...$parameters);
|
||||
}
|
||||
}
|
||||
|
@@ -3,7 +3,6 @@
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
use Illuminate\Cache\Console\ClearCommand;
|
||||
|
||||
class CacheServiceProvider extends ServiceProvider
|
||||
{
|
||||
@@ -32,22 +31,6 @@ class CacheServiceProvider extends ServiceProvider
|
||||
$this->app->singleton('memcached.connector', function () {
|
||||
return new MemcachedConnector;
|
||||
});
|
||||
|
||||
$this->registerCommands();
|
||||
}
|
||||
|
||||
/**
|
||||
* Register the cache related console commands.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function registerCommands()
|
||||
{
|
||||
$this->app->singleton('command.cache.clear', function ($app) {
|
||||
return new ClearCommand($app['cache']);
|
||||
});
|
||||
|
||||
$this->commands('command.cache.clear');
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -58,7 +41,7 @@ class CacheServiceProvider extends ServiceProvider
|
||||
public function provides()
|
||||
{
|
||||
return [
|
||||
'cache', 'cache.store', 'memcached.connector', 'command.cache.clear',
|
||||
'cache', 'cache.store', 'memcached.connector',
|
||||
];
|
||||
}
|
||||
}
|
||||
|
@@ -54,7 +54,7 @@ class CacheTableCommand extends Command
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function fire()
|
||||
public function handle()
|
||||
{
|
||||
$fullPath = $this->createBaseMigration();
|
||||
|
||||
|
@@ -4,6 +4,7 @@ namespace Illuminate\Cache\Console;
|
||||
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Cache\CacheManager;
|
||||
use Illuminate\Filesystem\Filesystem;
|
||||
use Symfony\Component\Console\Input\InputOption;
|
||||
use Symfony\Component\Console\Input\InputArgument;
|
||||
|
||||
@@ -30,17 +31,26 @@ class ClearCommand extends Command
|
||||
*/
|
||||
protected $cache;
|
||||
|
||||
/**
|
||||
* The filesystem instance.
|
||||
*
|
||||
* @var \Illuminate\Filesystem\Filesystem
|
||||
*/
|
||||
protected $files;
|
||||
|
||||
/**
|
||||
* Create a new cache clear command instance.
|
||||
*
|
||||
* @param \Illuminate\Cache\CacheManager $cache
|
||||
* @param \Illuminate\Filesystem\Filesystem $files
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(CacheManager $cache)
|
||||
public function __construct(CacheManager $cache, Filesystem $files)
|
||||
{
|
||||
parent::__construct();
|
||||
|
||||
$this->cache = $cache;
|
||||
$this->files = $files;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -50,21 +60,55 @@ class ClearCommand extends Command
|
||||
*/
|
||||
public function handle()
|
||||
{
|
||||
$tags = array_filter(explode(',', $this->option('tags')));
|
||||
$this->laravel['events']->fire(
|
||||
'cache:clearing', [$this->argument('store'), $this->tags()]
|
||||
);
|
||||
|
||||
$cache = $this->cache->store($store = $this->argument('store'));
|
||||
$this->cache()->flush();
|
||||
|
||||
$this->laravel['events']->fire('cache:clearing', [$store, $tags]);
|
||||
$this->flushFacades();
|
||||
|
||||
if (! empty($tags)) {
|
||||
$cache->tags($tags)->flush();
|
||||
} else {
|
||||
$cache->flush();
|
||||
}
|
||||
$this->laravel['events']->fire(
|
||||
'cache:cleared', [$this->argument('store'), $this->tags()]
|
||||
);
|
||||
|
||||
$this->info('Cache cleared successfully.');
|
||||
}
|
||||
|
||||
$this->laravel['events']->fire('cache:cleared', [$store, $tags]);
|
||||
/**
|
||||
* Flush the real-time facades stored in the cache directory.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function flushFacades()
|
||||
{
|
||||
foreach ($this->files->files(storage_path('framework/cache')) as $file) {
|
||||
if (preg_match('/facade-.*\.php$/', $file)) {
|
||||
$this->files->delete($file);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the cache instance for the command.
|
||||
*
|
||||
* @return \Illuminate\Cache\Repository
|
||||
*/
|
||||
protected function cache()
|
||||
{
|
||||
$cache = $this->cache->store($this->argument('store'));
|
||||
|
||||
return empty($this->tags()) ? $cache : $cache->tags($this->tags());
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the tags passed to the command.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
protected function tags()
|
||||
{
|
||||
return array_filter(explode(',', $this->option('tags')));
|
||||
}
|
||||
|
||||
/**
|
||||
|
57
vendor/laravel/framework/src/Illuminate/Cache/Console/ForgetCommand.php
vendored
Normal file
57
vendor/laravel/framework/src/Illuminate/Cache/Console/ForgetCommand.php
vendored
Normal file
@@ -0,0 +1,57 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Cache\Console;
|
||||
|
||||
use Illuminate\Console\Command;
|
||||
use Illuminate\Cache\CacheManager;
|
||||
|
||||
class ForgetCommand extends Command
|
||||
{
|
||||
/**
|
||||
* The console command name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $signature = 'cache:forget {key : The key to remove} {store? : The store to remove the key from}';
|
||||
|
||||
/**
|
||||
* The console command description.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $description = 'Remove an item from the cache';
|
||||
|
||||
/**
|
||||
* The cache manager instance.
|
||||
*
|
||||
* @var \Illuminate\Cache\CacheManager
|
||||
*/
|
||||
protected $cache;
|
||||
|
||||
/**
|
||||
* Create a new cache clear command instance.
|
||||
*
|
||||
* @param \Illuminate\Cache\CacheManager $cache
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(CacheManager $cache)
|
||||
{
|
||||
parent::__construct();
|
||||
|
||||
$this->cache = $cache;
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute the console command.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function handle()
|
||||
{
|
||||
$this->cache->store($this->argument('store'))->forget(
|
||||
$this->argument('key')
|
||||
);
|
||||
|
||||
$this->info('The ['.$this->argument('key').'] key has been removed from the cache.');
|
||||
}
|
||||
}
|
@@ -1,5 +1,6 @@
|
||||
<?php
|
||||
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
|
||||
@@ -14,7 +15,7 @@ class CreateCacheTable extends Migration
|
||||
{
|
||||
Schema::create('cache', function (Blueprint $table) {
|
||||
$table->string('key')->unique();
|
||||
$table->text('value');
|
||||
$table->mediumText('value');
|
||||
$table->integer('expiration');
|
||||
});
|
||||
}
|
||||
@@ -26,6 +27,6 @@ class CreateCacheTable extends Migration
|
||||
*/
|
||||
public function down()
|
||||
{
|
||||
Schema::drop('cache');
|
||||
Schema::dropIfExists('cache');
|
||||
}
|
||||
}
|
||||
|
@@ -5,12 +5,12 @@ namespace Illuminate\Cache;
|
||||
use Closure;
|
||||
use Exception;
|
||||
use Illuminate\Contracts\Cache\Store;
|
||||
use Illuminate\Support\InteractsWithTime;
|
||||
use Illuminate\Database\ConnectionInterface;
|
||||
use Illuminate\Contracts\Encryption\Encrypter as EncrypterContract;
|
||||
|
||||
class DatabaseStore implements Store
|
||||
{
|
||||
use RetrievesMultipleKeys;
|
||||
use InteractsWithTime, RetrievesMultipleKeys;
|
||||
|
||||
/**
|
||||
* The database connection instance.
|
||||
@@ -19,13 +19,6 @@ class DatabaseStore implements Store
|
||||
*/
|
||||
protected $connection;
|
||||
|
||||
/**
|
||||
* The encrypter instance.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Encryption\Encrypter
|
||||
*/
|
||||
protected $encrypter;
|
||||
|
||||
/**
|
||||
* The name of the cache table.
|
||||
*
|
||||
@@ -44,16 +37,14 @@ class DatabaseStore implements Store
|
||||
* Create a new database store.
|
||||
*
|
||||
* @param \Illuminate\Database\ConnectionInterface $connection
|
||||
* @param \Illuminate\Contracts\Encryption\Encrypter $encrypter
|
||||
* @param string $table
|
||||
* @param string $prefix
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(ConnectionInterface $connection, EncrypterContract $encrypter, $table, $prefix = '')
|
||||
public function __construct(ConnectionInterface $connection, $table, $prefix = '')
|
||||
{
|
||||
$this->table = $table;
|
||||
$this->prefix = $prefix;
|
||||
$this->encrypter = $encrypter;
|
||||
$this->connection = $connection;
|
||||
}
|
||||
|
||||
@@ -72,19 +63,22 @@ class DatabaseStore implements Store
|
||||
// If we have a cache record we will check the expiration time against current
|
||||
// time on the system and see if the record has expired. If it has, we will
|
||||
// remove the records from the database table so it isn't returned again.
|
||||
if (! is_null($cache)) {
|
||||
if (is_array($cache)) {
|
||||
$cache = (object) $cache;
|
||||
}
|
||||
|
||||
if (time() >= $cache->expiration) {
|
||||
$this->forget($key);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
return $this->encrypter->decrypt($cache->value);
|
||||
if (is_null($cache)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$cache = is_array($cache) ? (object) $cache : $cache;
|
||||
|
||||
// If this cache expiration date is past the current time, we will remove this
|
||||
// item from the cache. Then we will return a null value since the cache is
|
||||
// expired. We will use "Carbon" to make this comparison with the column.
|
||||
if ($this->currentTime() >= $cache->expiration) {
|
||||
$this->forget($key);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
return unserialize($cache->value);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -92,24 +86,21 @@ class DatabaseStore implements Store
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes)
|
||||
{
|
||||
$key = $this->prefix.$key;
|
||||
|
||||
// All of the cached values in the database are encrypted in case this is used
|
||||
// as a session data store by the consumer. We'll also calculate the expire
|
||||
// time and place that on the table so we will check it on our retrieval.
|
||||
$value = $this->encrypter->encrypt($value);
|
||||
$value = serialize($value);
|
||||
|
||||
$expiration = $this->getTime() + ($minutes * 60);
|
||||
$expiration = $this->getTime() + (int) ($minutes * 60);
|
||||
|
||||
try {
|
||||
$this->table()->insert(compact('key', 'value', 'expiration'));
|
||||
} catch (Exception $e) {
|
||||
$this->table()->where('key', '=', $key)->update(compact('value', 'expiration'));
|
||||
$this->table()->where('key', $key)->update(compact('value', 'expiration'));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -154,25 +145,34 @@ class DatabaseStore implements Store
|
||||
return $this->connection->transaction(function () use ($key, $value, $callback) {
|
||||
$prefixed = $this->prefix.$key;
|
||||
|
||||
$cache = $this->table()->where('key', $prefixed)->lockForUpdate()->first();
|
||||
$cache = $this->table()->where('key', $prefixed)
|
||||
->lockForUpdate()->first();
|
||||
|
||||
// If there is no value in the cache, we will return false here. Otherwise the
|
||||
// value will be decrypted and we will proceed with this function to either
|
||||
// increment or decrement this value based on the given action callbacks.
|
||||
if (is_null($cache)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (is_array($cache)) {
|
||||
$cache = (object) $cache;
|
||||
}
|
||||
$cache = is_array($cache) ? (object) $cache : $cache;
|
||||
|
||||
$current = $this->encrypter->decrypt($cache->value);
|
||||
$current = unserialize($cache->value);
|
||||
|
||||
// Here we'll call this callback function that was given to the function which
|
||||
// is used to either increment or decrement the function. We use a callback
|
||||
// so we do not have to recreate all this logic in each of the functions.
|
||||
$new = $callback((int) $current, $value);
|
||||
|
||||
if (! is_numeric($current)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Here we will update the values in the table. We will also encrypt the value
|
||||
// since database cache values are encrypted by default with secure storage
|
||||
// that can't be easily read. We will return the new value after storing.
|
||||
$this->table()->where('key', $prefixed)->update([
|
||||
'value' => $this->encrypter->encrypt($new),
|
||||
'value' => serialize($new),
|
||||
]);
|
||||
|
||||
return $new;
|
||||
@@ -186,7 +186,7 @@ class DatabaseStore implements Store
|
||||
*/
|
||||
protected function getTime()
|
||||
{
|
||||
return time();
|
||||
return $this->currentTime();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -217,11 +217,11 @@ class DatabaseStore implements Store
|
||||
/**
|
||||
* Remove all items from the cache.
|
||||
*
|
||||
* @return void
|
||||
* @return bool
|
||||
*/
|
||||
public function flush()
|
||||
{
|
||||
$this->table()->delete();
|
||||
return (bool) $this->table()->delete();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -244,16 +244,6 @@ class DatabaseStore implements Store
|
||||
return $this->connection;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the encrypter instance.
|
||||
*
|
||||
* @return \Illuminate\Contracts\Encryption\Encrypter
|
||||
*/
|
||||
public function getEncrypter()
|
||||
{
|
||||
return $this->encrypter;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the cache key prefix.
|
||||
*
|
||||
|
46
vendor/laravel/framework/src/Illuminate/Cache/Events/CacheEvent.php
vendored
Normal file
46
vendor/laravel/framework/src/Illuminate/Cache/Events/CacheEvent.php
vendored
Normal file
@@ -0,0 +1,46 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Cache\Events;
|
||||
|
||||
abstract class CacheEvent
|
||||
{
|
||||
/**
|
||||
* The key of the event.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $key;
|
||||
|
||||
/**
|
||||
* The tags that were assigned to the key.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
public $tags;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $key
|
||||
* @param array $tags
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($key, array $tags = [])
|
||||
{
|
||||
$this->key = $key;
|
||||
$this->tags = $tags;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the tags for the cache event.
|
||||
*
|
||||
* @param array $tags
|
||||
* @return $this
|
||||
*/
|
||||
public function setTags($tags)
|
||||
{
|
||||
$this->tags = $tags;
|
||||
|
||||
return $this;
|
||||
}
|
||||
}
|
@@ -2,15 +2,8 @@
|
||||
|
||||
namespace Illuminate\Cache\Events;
|
||||
|
||||
class CacheHit
|
||||
class CacheHit extends CacheEvent
|
||||
{
|
||||
/**
|
||||
* The key that was hit.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $key;
|
||||
|
||||
/**
|
||||
* The value that was retrieved.
|
||||
*
|
||||
@@ -18,13 +11,6 @@ class CacheHit
|
||||
*/
|
||||
public $value;
|
||||
|
||||
/**
|
||||
* The tags that were assigned to the key.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
public $tags;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
@@ -35,8 +21,8 @@ class CacheHit
|
||||
*/
|
||||
public function __construct($key, $value, array $tags = [])
|
||||
{
|
||||
$this->key = $key;
|
||||
$this->tags = $tags;
|
||||
parent::__construct($key, $tags);
|
||||
|
||||
$this->value = $value;
|
||||
}
|
||||
}
|
||||
|
@@ -2,32 +2,7 @@
|
||||
|
||||
namespace Illuminate\Cache\Events;
|
||||
|
||||
class CacheMissed
|
||||
class CacheMissed extends CacheEvent
|
||||
{
|
||||
/**
|
||||
* The key that was missed.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $key;
|
||||
|
||||
/**
|
||||
* The tags that were assigned to the key.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
public $tags;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $key
|
||||
* @param array $tags
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($key, array $tags = [])
|
||||
{
|
||||
$this->key = $key;
|
||||
$this->tags = $tags;
|
||||
}
|
||||
//
|
||||
}
|
||||
|
@@ -2,32 +2,7 @@
|
||||
|
||||
namespace Illuminate\Cache\Events;
|
||||
|
||||
class KeyForgotten
|
||||
class KeyForgotten extends CacheEvent
|
||||
{
|
||||
/**
|
||||
* The key that was forgotten.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $key;
|
||||
|
||||
/**
|
||||
* The tags that were assigned to the key.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
public $tags;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $key
|
||||
* @param array $tags
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($key, $tags = [])
|
||||
{
|
||||
$this->key = $key;
|
||||
$this->tags = $tags;
|
||||
}
|
||||
//
|
||||
}
|
||||
|
@@ -2,15 +2,8 @@
|
||||
|
||||
namespace Illuminate\Cache\Events;
|
||||
|
||||
class KeyWritten
|
||||
class KeyWritten extends CacheEvent
|
||||
{
|
||||
/**
|
||||
* The key that was written.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $key;
|
||||
|
||||
/**
|
||||
* The value that was written.
|
||||
*
|
||||
@@ -25,13 +18,6 @@ class KeyWritten
|
||||
*/
|
||||
public $minutes;
|
||||
|
||||
/**
|
||||
* The tags that were assigned to the key.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
public $tags;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
@@ -43,8 +29,8 @@ class KeyWritten
|
||||
*/
|
||||
public function __construct($key, $value, $minutes, $tags = [])
|
||||
{
|
||||
$this->key = $key;
|
||||
$this->tags = $tags;
|
||||
parent::__construct($key, $tags);
|
||||
|
||||
$this->value = $value;
|
||||
$this->minutes = $minutes;
|
||||
}
|
||||
|
@@ -3,13 +3,13 @@
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Exception;
|
||||
use Illuminate\Support\Arr;
|
||||
use Illuminate\Filesystem\Filesystem;
|
||||
use Illuminate\Contracts\Cache\Store;
|
||||
use Illuminate\Filesystem\Filesystem;
|
||||
use Illuminate\Support\InteractsWithTime;
|
||||
|
||||
class FileStore implements Store
|
||||
{
|
||||
use RetrievesMultipleKeys;
|
||||
use InteractsWithTime, RetrievesMultipleKeys;
|
||||
|
||||
/**
|
||||
* The Illuminate Filesystem instance.
|
||||
@@ -46,47 +46,7 @@ class FileStore implements Store
|
||||
*/
|
||||
public function get($key)
|
||||
{
|
||||
return Arr::get($this->getPayload($key), 'data');
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve an item and expiry time from the cache by key.
|
||||
*
|
||||
* @param string $key
|
||||
* @return array
|
||||
*/
|
||||
protected function getPayload($key)
|
||||
{
|
||||
$path = $this->path($key);
|
||||
|
||||
// If the file doesn't exists, we obviously can't return the cache so we will
|
||||
// just return null. Otherwise, we'll get the contents of the file and get
|
||||
// the expiration UNIX timestamps from the start of the file's contents.
|
||||
try {
|
||||
$expire = substr(
|
||||
$contents = $this->files->get($path, true), 0, 10
|
||||
);
|
||||
} catch (Exception $e) {
|
||||
return ['data' => null, 'time' => null];
|
||||
}
|
||||
|
||||
// If the current time is greater than expiration timestamps we will delete
|
||||
// the file and return null. This helps clean up the old files and keeps
|
||||
// this directory much cleaner for us as old files aren't hanging out.
|
||||
if (time() >= $expire) {
|
||||
$this->forget($key);
|
||||
|
||||
return ['data' => null, 'time' => null];
|
||||
}
|
||||
|
||||
$data = unserialize(substr($contents, 10));
|
||||
|
||||
// Next, we'll extract the number of minutes that are remaining for a cache
|
||||
// so that we can properly retain the time for things like the increment
|
||||
// operation that may be performed on the cache. We'll round this out.
|
||||
$time = ceil(($expire - time()) / 60);
|
||||
|
||||
return compact('data', 'time');
|
||||
return $this->getPayload($key)['data'] ?? null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -94,16 +54,16 @@ class FileStore implements Store
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes)
|
||||
{
|
||||
$value = $this->expiration($minutes).serialize($value);
|
||||
$this->ensureCacheDirectoryExists($path = $this->path($key));
|
||||
|
||||
$this->createCacheDirectory($path = $this->path($key));
|
||||
|
||||
$this->files->put($path, $value, true);
|
||||
$this->files->put(
|
||||
$path, $this->expiration($minutes).serialize($value), true
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -112,7 +72,7 @@ class FileStore implements Store
|
||||
* @param string $path
|
||||
* @return void
|
||||
*/
|
||||
protected function createCacheDirectory($path)
|
||||
protected function ensureCacheDirectoryExists($path)
|
||||
{
|
||||
if (! $this->files->exists(dirname($path))) {
|
||||
$this->files->makeDirectory(dirname($path), 0777, true, true);
|
||||
@@ -130,11 +90,9 @@ class FileStore implements Store
|
||||
{
|
||||
$raw = $this->getPayload($key);
|
||||
|
||||
$int = ((int) $raw['data']) + $value;
|
||||
|
||||
$this->put($key, $int, (int) $raw['time']);
|
||||
|
||||
return $int;
|
||||
return tap(((int) $raw['data']) + $value, function ($newValue) use ($key, $raw) {
|
||||
$this->put($key, $newValue, $raw['time']);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -169,9 +127,7 @@ class FileStore implements Store
|
||||
*/
|
||||
public function forget($key)
|
||||
{
|
||||
$file = $this->path($key);
|
||||
|
||||
if ($this->files->exists($file)) {
|
||||
if ($this->files->exists($file = $this->path($key))) {
|
||||
return $this->files->delete($file);
|
||||
}
|
||||
|
||||
@@ -181,15 +137,71 @@ class FileStore implements Store
|
||||
/**
|
||||
* Remove all items from the cache.
|
||||
*
|
||||
* @return void
|
||||
* @return bool
|
||||
*/
|
||||
public function flush()
|
||||
{
|
||||
if ($this->files->isDirectory($this->directory)) {
|
||||
foreach ($this->files->directories($this->directory) as $directory) {
|
||||
$this->files->deleteDirectory($directory);
|
||||
if (! $this->files->isDirectory($this->directory)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
foreach ($this->files->directories($this->directory) as $directory) {
|
||||
if (! $this->files->deleteDirectory($directory)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve an item and expiry time from the cache by key.
|
||||
*
|
||||
* @param string $key
|
||||
* @return array
|
||||
*/
|
||||
protected function getPayload($key)
|
||||
{
|
||||
$path = $this->path($key);
|
||||
|
||||
// If the file doesn't exist, we obviously cannot return the cache so we will
|
||||
// just return null. Otherwise, we'll get the contents of the file and get
|
||||
// the expiration UNIX timestamps from the start of the file's contents.
|
||||
try {
|
||||
$expire = substr(
|
||||
$contents = $this->files->get($path, true), 0, 10
|
||||
);
|
||||
} catch (Exception $e) {
|
||||
return $this->emptyPayload();
|
||||
}
|
||||
|
||||
// If the current time is greater than expiration timestamps we will delete
|
||||
// the file and return null. This helps clean up the old files and keeps
|
||||
// this directory much cleaner for us as old files aren't hanging out.
|
||||
if ($this->currentTime() >= $expire) {
|
||||
$this->forget($key);
|
||||
|
||||
return $this->emptyPayload();
|
||||
}
|
||||
|
||||
$data = unserialize(substr($contents, 10));
|
||||
|
||||
// Next, we'll extract the number of minutes that are remaining for a cache
|
||||
// so that we can properly retain the time for things like the increment
|
||||
// operation that may be performed on this cache on a later operation.
|
||||
$time = ($expire - $this->currentTime()) / 60;
|
||||
|
||||
return compact('data', 'time');
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a default empty payload for the cache.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
protected function emptyPayload()
|
||||
{
|
||||
return ['data' => null, 'time' => null];
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -208,18 +220,14 @@ class FileStore implements Store
|
||||
/**
|
||||
* Get the expiration time based on the given minutes.
|
||||
*
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return int
|
||||
*/
|
||||
protected function expiration($minutes)
|
||||
{
|
||||
$time = time() + ($minutes * 60);
|
||||
$time = $this->availableAt((int) ($minutes * 60));
|
||||
|
||||
if ($minutes === 0 || $time > 9999999999) {
|
||||
return 9999999999;
|
||||
}
|
||||
|
||||
return (int) $time;
|
||||
return $minutes === 0 || $time > 9999999999 ? 9999999999 : (int) $time;
|
||||
}
|
||||
|
||||
/**
|
||||
|
93
vendor/laravel/framework/src/Illuminate/Cache/Lock.php
vendored
Normal file
93
vendor/laravel/framework/src/Illuminate/Cache/Lock.php
vendored
Normal file
@@ -0,0 +1,93 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Illuminate\Support\InteractsWithTime;
|
||||
use Illuminate\Contracts\Cache\LockTimeoutException;
|
||||
|
||||
abstract class Lock
|
||||
{
|
||||
use InteractsWithTime;
|
||||
|
||||
/**
|
||||
* The name of the lock.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $name;
|
||||
|
||||
/**
|
||||
* The number of seconds the lock should be maintained.
|
||||
*
|
||||
* @var int
|
||||
*/
|
||||
protected $seconds;
|
||||
|
||||
/**
|
||||
* Create a new lock instance.
|
||||
*
|
||||
* @param string $name
|
||||
* @param int $seconds
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($name, $seconds)
|
||||
{
|
||||
$this->name = $name;
|
||||
$this->seconds = $seconds;
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to acquire the lock.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
abstract public function acquire();
|
||||
|
||||
/**
|
||||
* Attempt to acquire the lock.
|
||||
*
|
||||
* @param callable|null $callback
|
||||
* @return bool
|
||||
*/
|
||||
public function get($callback = null)
|
||||
{
|
||||
$result = $this->acquire();
|
||||
|
||||
if ($result && is_callable($callback)) {
|
||||
return tap($callback(), function () {
|
||||
$this->release();
|
||||
});
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to acquire the lock for the given number of seconds.
|
||||
*
|
||||
* @param int $seconds
|
||||
* @param callable|null $callback
|
||||
* @return bool
|
||||
* @throws \Illuminate\Contracts\Cache\LockTimeoutException
|
||||
*/
|
||||
public function block($seconds, $callback = null)
|
||||
{
|
||||
$starting = $this->currentTime();
|
||||
|
||||
while (! $this->acquire()) {
|
||||
usleep(250 * 1000);
|
||||
|
||||
if ($this->currentTime() - $seconds >= $starting) {
|
||||
throw new LockTimeoutException;
|
||||
}
|
||||
}
|
||||
|
||||
if (is_callable($callback)) {
|
||||
return tap($callback(), function () {
|
||||
$this->release();
|
||||
});
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
@@ -3,7 +3,6 @@
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Memcached;
|
||||
use RuntimeException;
|
||||
|
||||
class MemcachedConnector
|
||||
{
|
||||
@@ -11,31 +10,26 @@ class MemcachedConnector
|
||||
* Create a new Memcached connection.
|
||||
*
|
||||
* @param array $servers
|
||||
* @param string|null $connectionId
|
||||
* @param array $options
|
||||
* @param array $credentials
|
||||
* @return \Memcached
|
||||
*
|
||||
* @throws \RuntimeException
|
||||
*/
|
||||
public function connect(array $servers)
|
||||
public function connect(array $servers, $connectionId = null, array $options = [], array $credentials = [])
|
||||
{
|
||||
$memcached = $this->getMemcached();
|
||||
$memcached = $this->getMemcached(
|
||||
$connectionId, $credentials, $options
|
||||
);
|
||||
|
||||
// For each server in the array, we'll just extract the configuration and add
|
||||
// the server to the Memcached connection. Once we have added all of these
|
||||
// servers we'll verify the connection is successful and return it back.
|
||||
foreach ($servers as $server) {
|
||||
$memcached->addServer(
|
||||
$server['host'], $server['port'], $server['weight']
|
||||
);
|
||||
}
|
||||
|
||||
$memcachedStatus = $memcached->getVersion();
|
||||
|
||||
if (! is_array($memcachedStatus)) {
|
||||
throw new RuntimeException('No Memcached servers added.');
|
||||
}
|
||||
|
||||
if (in_array('255.255.255', $memcachedStatus) && count(array_unique($memcachedStatus)) === 1) {
|
||||
throw new RuntimeException('Could not establish Memcached connection.');
|
||||
if (! $memcached->getServerList()) {
|
||||
// For each server in the array, we'll just extract the configuration and add
|
||||
// the server to the Memcached connection. Once we have added all of these
|
||||
// servers we'll verify the connection is successful and return it back.
|
||||
foreach ($servers as $server) {
|
||||
$memcached->addServer(
|
||||
$server['host'], $server['port'], $server['weight']
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
return $memcached;
|
||||
@@ -44,10 +38,50 @@ class MemcachedConnector
|
||||
/**
|
||||
* Get a new Memcached instance.
|
||||
*
|
||||
* @param string|null $connectionId
|
||||
* @param array $credentials
|
||||
* @param array $options
|
||||
* @return \Memcached
|
||||
*/
|
||||
protected function getMemcached()
|
||||
protected function getMemcached($connectionId, array $credentials, array $options)
|
||||
{
|
||||
return new Memcached;
|
||||
$memcached = $this->createMemcachedInstance($connectionId);
|
||||
|
||||
if (count($credentials) == 2) {
|
||||
$this->setCredentials($memcached, $credentials);
|
||||
}
|
||||
|
||||
if (count($options)) {
|
||||
$memcached->setOptions($options);
|
||||
}
|
||||
|
||||
return $memcached;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create the Memcached instance.
|
||||
*
|
||||
* @param string|null $connectionId
|
||||
* @return \Memcached
|
||||
*/
|
||||
protected function createMemcachedInstance($connectionId)
|
||||
{
|
||||
return empty($connectionId) ? new Memcached : new Memcached($connectionId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the SASL credentials on the Memcached connection.
|
||||
*
|
||||
* @param \Memcached $memcached
|
||||
* @param array $credentials
|
||||
* @return void
|
||||
*/
|
||||
protected function setCredentials($memcached, $credentials)
|
||||
{
|
||||
list($username, $password) = $credentials;
|
||||
|
||||
$memcached->setOption(Memcached::OPT_BINARY_PROTOCOL, true);
|
||||
|
||||
$memcached->setSaslAuthData($username, $password);
|
||||
}
|
||||
}
|
||||
|
52
vendor/laravel/framework/src/Illuminate/Cache/MemcachedLock.php
vendored
Normal file
52
vendor/laravel/framework/src/Illuminate/Cache/MemcachedLock.php
vendored
Normal file
@@ -0,0 +1,52 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Illuminate\Contracts\Cache\Lock as LockContract;
|
||||
|
||||
class MemcachedLock extends Lock implements LockContract
|
||||
{
|
||||
/**
|
||||
* The Memcached instance.
|
||||
*
|
||||
* @var \Memcached
|
||||
*/
|
||||
protected $memcached;
|
||||
|
||||
/**
|
||||
* Create a new lock instance.
|
||||
*
|
||||
* @param \Memcached $memcached
|
||||
* @param string $name
|
||||
* @param int $seconds
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($memcached, $name, $seconds)
|
||||
{
|
||||
parent::__construct($name, $seconds);
|
||||
|
||||
$this->memcached = $memcached;
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to acquire the lock.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function acquire()
|
||||
{
|
||||
return $this->memcached->add(
|
||||
$this->name, 1, $this->seconds
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Release the lock.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function release()
|
||||
{
|
||||
$this->memcached->delete($this->name);
|
||||
}
|
||||
}
|
@@ -3,10 +3,15 @@
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Memcached;
|
||||
use ReflectionMethod;
|
||||
use Illuminate\Contracts\Cache\Store;
|
||||
use Illuminate\Support\InteractsWithTime;
|
||||
use Illuminate\Contracts\Cache\LockProvider;
|
||||
|
||||
class MemcachedStore extends TaggableStore implements Store
|
||||
class MemcachedStore extends TaggableStore implements LockProvider, Store
|
||||
{
|
||||
use InteractsWithTime;
|
||||
|
||||
/**
|
||||
* The Memcached instance.
|
||||
*
|
||||
@@ -21,6 +26,13 @@ class MemcachedStore extends TaggableStore implements Store
|
||||
*/
|
||||
protected $prefix;
|
||||
|
||||
/**
|
||||
* Indicates whether we are using Memcached version >= 3.0.0.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
protected $onVersionThree;
|
||||
|
||||
/**
|
||||
* Create a new Memcached store.
|
||||
*
|
||||
@@ -32,12 +44,15 @@ class MemcachedStore extends TaggableStore implements Store
|
||||
{
|
||||
$this->setPrefix($prefix);
|
||||
$this->memcached = $memcached;
|
||||
|
||||
$this->onVersionThree = (new ReflectionMethod('Memcached', 'getMulti'))
|
||||
->getNumberOfParameters() == 2;
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve an item from the cache by key.
|
||||
*
|
||||
* @param string|array $key
|
||||
* @param string $key
|
||||
* @return mixed
|
||||
*/
|
||||
public function get($key)
|
||||
@@ -63,7 +78,13 @@ class MemcachedStore extends TaggableStore implements Store
|
||||
return $this->prefix.$key;
|
||||
}, $keys);
|
||||
|
||||
$values = $this->memcached->getMulti($prefixedKeys, null, Memcached::GET_PRESERVE_ORDER);
|
||||
if ($this->onVersionThree) {
|
||||
$values = $this->memcached->getMulti($prefixedKeys, Memcached::GET_PRESERVE_ORDER);
|
||||
} else {
|
||||
$null = null;
|
||||
|
||||
$values = $this->memcached->getMulti($prefixedKeys, $null, Memcached::GET_PRESERVE_ORDER);
|
||||
}
|
||||
|
||||
if ($this->memcached->getResultCode() != 0) {
|
||||
return array_fill_keys($keys, null);
|
||||
@@ -77,19 +98,19 @@ class MemcachedStore extends TaggableStore implements Store
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes)
|
||||
{
|
||||
$this->memcached->set($this->prefix.$key, $value, $minutes * 60);
|
||||
$this->memcached->set($this->prefix.$key, $value, $this->toTimestamp($minutes));
|
||||
}
|
||||
|
||||
/**
|
||||
* Store multiple items in the cache for a given number of minutes.
|
||||
*
|
||||
* @param array $values
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function putMany(array $values, $minutes)
|
||||
@@ -100,7 +121,7 @@ class MemcachedStore extends TaggableStore implements Store
|
||||
$prefixedValues[$this->prefix.$key] = $value;
|
||||
}
|
||||
|
||||
$this->memcached->setMulti($prefixedValues, $minutes * 60);
|
||||
$this->memcached->setMulti($prefixedValues, $this->toTimestamp($minutes));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -108,12 +129,12 @@ class MemcachedStore extends TaggableStore implements Store
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return bool
|
||||
*/
|
||||
public function add($key, $value, $minutes)
|
||||
{
|
||||
return $this->memcached->add($this->prefix.$key, $value, $minutes * 60);
|
||||
return $this->memcached->add($this->prefix.$key, $value, $this->toTimestamp($minutes));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -152,6 +173,18 @@ class MemcachedStore extends TaggableStore implements Store
|
||||
$this->put($key, $value, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a lock instance.
|
||||
*
|
||||
* @param string $name
|
||||
* @param int $seconds
|
||||
* @return \Illuminate\Contracts\Cache\Lock
|
||||
*/
|
||||
public function lock($name, $seconds = 0)
|
||||
{
|
||||
return new MemcachedLock($this->memcached, $this->prefix.$name, $seconds);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove an item from the cache.
|
||||
*
|
||||
@@ -166,11 +199,22 @@ class MemcachedStore extends TaggableStore implements Store
|
||||
/**
|
||||
* Remove all items from the cache.
|
||||
*
|
||||
* @return void
|
||||
* @return bool
|
||||
*/
|
||||
public function flush()
|
||||
{
|
||||
$this->memcached->flush();
|
||||
return $this->memcached->flush();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the UNIX timestamp for the given number of minutes.
|
||||
*
|
||||
* @param int $minutes
|
||||
* @return int
|
||||
*/
|
||||
protected function toTimestamp($minutes)
|
||||
{
|
||||
return $minutes > 0 ? $this->availableAt($minutes * 60) : 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@@ -31,7 +31,7 @@ class NullStore extends TaggableStore implements Store
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes)
|
||||
@@ -89,11 +89,11 @@ class NullStore extends TaggableStore implements Store
|
||||
/**
|
||||
* Remove all items from the cache.
|
||||
*
|
||||
* @return void
|
||||
* @return bool
|
||||
*/
|
||||
public function flush()
|
||||
{
|
||||
//
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@@ -2,10 +2,13 @@
|
||||
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Illuminate\Support\InteractsWithTime;
|
||||
use Illuminate\Contracts\Cache\Repository as Cache;
|
||||
|
||||
class RateLimiter
|
||||
{
|
||||
use InteractsWithTime;
|
||||
|
||||
/**
|
||||
* The cache store implementation.
|
||||
*
|
||||
@@ -29,21 +32,17 @@ class RateLimiter
|
||||
*
|
||||
* @param string $key
|
||||
* @param int $maxAttempts
|
||||
* @param int $decayMinutes
|
||||
* @param float|int $decayMinutes
|
||||
* @return bool
|
||||
*/
|
||||
public function tooManyAttempts($key, $maxAttempts, $decayMinutes = 1)
|
||||
{
|
||||
if ($this->cache->has($key.':lockout')) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if ($this->attempts($key) > $maxAttempts) {
|
||||
$this->cache->add($key.':lockout', time() + ($decayMinutes * 60), $decayMinutes);
|
||||
if ($this->attempts($key) >= $maxAttempts) {
|
||||
if ($this->cache->has($key.':timer')) {
|
||||
return true;
|
||||
}
|
||||
|
||||
$this->resetAttempts($key);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
@@ -53,14 +52,24 @@ class RateLimiter
|
||||
* Increment the counter for a given key for a given decay time.
|
||||
*
|
||||
* @param string $key
|
||||
* @param int $decayMinutes
|
||||
* @param float|int $decayMinutes
|
||||
* @return int
|
||||
*/
|
||||
public function hit($key, $decayMinutes = 1)
|
||||
{
|
||||
$this->cache->add($key, 1, $decayMinutes);
|
||||
$this->cache->add(
|
||||
$key.':timer', $this->availableAt($decayMinutes * 60), $decayMinutes
|
||||
);
|
||||
|
||||
return (int) $this->cache->increment($key);
|
||||
$added = $this->cache->add($key, 0, $decayMinutes);
|
||||
|
||||
$hits = (int) $this->cache->increment($key);
|
||||
|
||||
if (! $added && $hits == 1) {
|
||||
$this->cache->put($key, 1, $decayMinutes);
|
||||
}
|
||||
|
||||
return $hits;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -96,11 +105,11 @@ class RateLimiter
|
||||
{
|
||||
$attempts = $this->attempts($key);
|
||||
|
||||
return $attempts === 0 ? $maxAttempts : $maxAttempts - $attempts + 1;
|
||||
return $maxAttempts - $attempts;
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear the hits and lockout for the given key.
|
||||
* Clear the hits and lockout timer for the given key.
|
||||
*
|
||||
* @param string $key
|
||||
* @return void
|
||||
@@ -109,7 +118,7 @@ class RateLimiter
|
||||
{
|
||||
$this->resetAttempts($key);
|
||||
|
||||
$this->cache->forget($key.':lockout');
|
||||
$this->cache->forget($key.':timer');
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -120,6 +129,6 @@ class RateLimiter
|
||||
*/
|
||||
public function availableIn($key)
|
||||
{
|
||||
return $this->cache->get($key.':lockout') - time();
|
||||
return $this->cache->get($key.':timer') - $this->currentTime();
|
||||
}
|
||||
}
|
||||
|
56
vendor/laravel/framework/src/Illuminate/Cache/RedisLock.php
vendored
Normal file
56
vendor/laravel/framework/src/Illuminate/Cache/RedisLock.php
vendored
Normal file
@@ -0,0 +1,56 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Illuminate\Contracts\Cache\Lock as LockContract;
|
||||
|
||||
class RedisLock extends Lock implements LockContract
|
||||
{
|
||||
/**
|
||||
* The Redis factory implementation.
|
||||
*
|
||||
* @var \Illuminate\Redis\Connections\Connection
|
||||
*/
|
||||
protected $redis;
|
||||
|
||||
/**
|
||||
* Create a new lock instance.
|
||||
*
|
||||
* @param \Illuminate\Redis\Connections\Connection $redis
|
||||
* @param string $name
|
||||
* @param int $seconds
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($redis, $name, $seconds)
|
||||
{
|
||||
parent::__construct($name, $seconds);
|
||||
|
||||
$this->redis = $redis;
|
||||
}
|
||||
|
||||
/**
|
||||
* Attempt to acquire the lock.
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function acquire()
|
||||
{
|
||||
$result = $this->redis->setnx($this->name, 1);
|
||||
|
||||
if ($result === 1 && $this->seconds > 0) {
|
||||
$this->redis->expire($this->name, $this->seconds);
|
||||
}
|
||||
|
||||
return $result === 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Release the lock.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function release()
|
||||
{
|
||||
$this->redis->del($this->name);
|
||||
}
|
||||
}
|
@@ -3,14 +3,14 @@
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Illuminate\Contracts\Cache\Store;
|
||||
use Illuminate\Redis\Database as Redis;
|
||||
use Illuminate\Contracts\Redis\Factory as Redis;
|
||||
|
||||
class RedisStore extends TaggableStore implements Store
|
||||
{
|
||||
/**
|
||||
* The Redis database connection.
|
||||
* The Redis factory implementation.
|
||||
*
|
||||
* @var \Illuminate\Redis\Database
|
||||
* @var \Illuminate\Contracts\Redis\Factory
|
||||
*/
|
||||
protected $redis;
|
||||
|
||||
@@ -31,7 +31,7 @@ class RedisStore extends TaggableStore implements Store
|
||||
/**
|
||||
* Create a new Redis store.
|
||||
*
|
||||
* @param \Illuminate\Redis\Database $redis
|
||||
* @param \Illuminate\Contracts\Redis\Factory $redis
|
||||
* @param string $prefix
|
||||
* @param string $connection
|
||||
* @return void
|
||||
@@ -40,7 +40,7 @@ class RedisStore extends TaggableStore implements Store
|
||||
{
|
||||
$this->redis = $redis;
|
||||
$this->setPrefix($prefix);
|
||||
$this->connection = $connection;
|
||||
$this->setConnection($connection);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -51,9 +51,9 @@ class RedisStore extends TaggableStore implements Store
|
||||
*/
|
||||
public function get($key)
|
||||
{
|
||||
if (! is_null($value = $this->connection()->get($this->prefix.$key))) {
|
||||
return is_numeric($value) ? $value : unserialize($value);
|
||||
}
|
||||
$value = $this->connection()->get($this->prefix.$key);
|
||||
|
||||
return ! is_null($value) ? $this->unserialize($value) : null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -66,19 +66,17 @@ class RedisStore extends TaggableStore implements Store
|
||||
*/
|
||||
public function many(array $keys)
|
||||
{
|
||||
$return = [];
|
||||
$results = [];
|
||||
|
||||
$prefixedKeys = array_map(function ($key) {
|
||||
$values = $this->connection()->mget(array_map(function ($key) {
|
||||
return $this->prefix.$key;
|
||||
}, $keys);
|
||||
|
||||
$values = $this->connection()->mget($prefixedKeys);
|
||||
}, $keys));
|
||||
|
||||
foreach ($values as $index => $value) {
|
||||
$return[$keys[$index]] = is_numeric($value) ? $value : unserialize($value);
|
||||
$results[$keys[$index]] = ! is_null($value) ? $this->unserialize($value) : null;
|
||||
}
|
||||
|
||||
return $return;
|
||||
return $results;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -86,21 +84,21 @@ class RedisStore extends TaggableStore implements Store
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes)
|
||||
{
|
||||
$value = is_numeric($value) ? $value : serialize($value);
|
||||
|
||||
$this->connection()->setex($this->prefix.$key, (int) max(1, $minutes * 60), $value);
|
||||
$this->connection()->setex(
|
||||
$this->prefix.$key, (int) max(1, $minutes * 60), $this->serialize($value)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Store multiple items in the cache for a given number of minutes.
|
||||
*
|
||||
* @param array $values
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function putMany(array $values, $minutes)
|
||||
@@ -114,6 +112,23 @@ class RedisStore extends TaggableStore implements Store
|
||||
$this->connection()->exec();
|
||||
}
|
||||
|
||||
/**
|
||||
* Store an item in the cache if the key doesn't exist.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param float|int $minutes
|
||||
* @return bool
|
||||
*/
|
||||
public function add($key, $value, $minutes)
|
||||
{
|
||||
$lua = "return redis.call('exists',KEYS[1])<1 and redis.call('setex',KEYS[1],ARGV[2],ARGV[1])";
|
||||
|
||||
return (bool) $this->connection()->eval(
|
||||
$lua, 1, $this->prefix.$key, $this->serialize($value), (int) max(1, $minutes * 60)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Increment the value of an item in the cache.
|
||||
*
|
||||
@@ -147,9 +162,19 @@ class RedisStore extends TaggableStore implements Store
|
||||
*/
|
||||
public function forever($key, $value)
|
||||
{
|
||||
$value = is_numeric($value) ? $value : serialize($value);
|
||||
$this->connection()->set($this->prefix.$key, $this->serialize($value));
|
||||
}
|
||||
|
||||
$this->connection()->set($this->prefix.$key, $value);
|
||||
/**
|
||||
* Get a lock instance.
|
||||
*
|
||||
* @param string $name
|
||||
* @param int $seconds
|
||||
* @return \Illuminate\Contracts\Cache\Lock
|
||||
*/
|
||||
public function lock($name, $seconds = 0)
|
||||
{
|
||||
return new RedisLock($this->connection(), $this->prefix.$name, $seconds);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -166,11 +191,13 @@ class RedisStore extends TaggableStore implements Store
|
||||
/**
|
||||
* Remove all items from the cache.
|
||||
*
|
||||
* @return void
|
||||
* @return bool
|
||||
*/
|
||||
public function flush()
|
||||
{
|
||||
$this->connection()->flushdb();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -181,7 +208,9 @@ class RedisStore extends TaggableStore implements Store
|
||||
*/
|
||||
public function tags($names)
|
||||
{
|
||||
return new RedisTaggedCache($this, new TagSet($this, is_array($names) ? $names : func_get_args()));
|
||||
return new RedisTaggedCache(
|
||||
$this, new TagSet($this, is_array($names) ? $names : func_get_args())
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -208,7 +237,7 @@ class RedisStore extends TaggableStore implements Store
|
||||
/**
|
||||
* Get the Redis database instance.
|
||||
*
|
||||
* @return \Illuminate\Redis\Database
|
||||
* @return \Illuminate\Contracts\Redis\Factory
|
||||
*/
|
||||
public function getRedis()
|
||||
{
|
||||
@@ -235,4 +264,26 @@ class RedisStore extends TaggableStore implements Store
|
||||
{
|
||||
$this->prefix = ! empty($prefix) ? $prefix.':' : '';
|
||||
}
|
||||
|
||||
/**
|
||||
* Serialize the value.
|
||||
*
|
||||
* @param mixed $value
|
||||
* @return mixed
|
||||
*/
|
||||
protected function serialize($value)
|
||||
{
|
||||
return is_numeric($value) ? $value : serialize($value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Unserialize the value.
|
||||
*
|
||||
* @param mixed $value
|
||||
* @return mixed
|
||||
*/
|
||||
protected function unserialize($value)
|
||||
{
|
||||
return is_numeric($value) ? $value : unserialize($value);
|
||||
}
|
||||
}
|
||||
|
@@ -22,7 +22,7 @@ class RedisTaggedCache extends TaggedCache
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param \DateTime|int $minutes
|
||||
* @param \DateTime|float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes = null)
|
||||
@@ -93,7 +93,7 @@ class RedisTaggedCache extends TaggedCache
|
||||
*/
|
||||
protected function pushKeys($namespace, $key, $reference)
|
||||
{
|
||||
$fullKey = $this->getPrefix().sha1($namespace).':'.$key;
|
||||
$fullKey = $this->store->getPrefix().sha1($namespace).':'.$key;
|
||||
|
||||
foreach (explode('|', $namespace) as $segment) {
|
||||
$this->store->connection()->sadd($this->referenceKey($segment, $reference), $fullKey);
|
||||
@@ -146,7 +146,9 @@ class RedisTaggedCache extends TaggedCache
|
||||
$values = array_unique($this->store->connection()->smembers($referenceKey));
|
||||
|
||||
if (count($values) > 0) {
|
||||
call_user_func_array([$this->store->connection(), 'del'], $values);
|
||||
foreach (array_chunk($values, 1000) as $valuesChunk) {
|
||||
call_user_func_array([$this->store->connection(), 'del'], $valuesChunk);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -159,6 +161,6 @@ class RedisTaggedCache extends TaggedCache
|
||||
*/
|
||||
protected function referenceKey($segment, $suffix)
|
||||
{
|
||||
return $this->getPrefix().$segment.':'.$suffix;
|
||||
return $this->store->getPrefix().$segment.':'.$suffix;
|
||||
}
|
||||
}
|
||||
|
@@ -3,17 +3,26 @@
|
||||
namespace Illuminate\Cache;
|
||||
|
||||
use Closure;
|
||||
use DateTime;
|
||||
use ArrayAccess;
|
||||
use Carbon\Carbon;
|
||||
use DateTimeInterface;
|
||||
use BadMethodCallException;
|
||||
use Illuminate\Support\Carbon;
|
||||
use Illuminate\Cache\Events\CacheHit;
|
||||
use Illuminate\Contracts\Cache\Store;
|
||||
use Illuminate\Cache\Events\KeyWritten;
|
||||
use Illuminate\Cache\Events\CacheMissed;
|
||||
use Illuminate\Support\Traits\Macroable;
|
||||
use Illuminate\Cache\Events\KeyForgotten;
|
||||
use Illuminate\Support\InteractsWithTime;
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
use Illuminate\Contracts\Cache\Repository as CacheContract;
|
||||
|
||||
/**
|
||||
* @mixin \Illuminate\Contracts\Cache\Store
|
||||
*/
|
||||
class Repository implements CacheContract, ArrayAccess
|
||||
{
|
||||
use InteractsWithTime;
|
||||
use Macroable {
|
||||
__call as macroCall;
|
||||
}
|
||||
@@ -35,7 +44,7 @@ class Repository implements CacheContract, ArrayAccess
|
||||
/**
|
||||
* The default number of minutes to store items.
|
||||
*
|
||||
* @var int
|
||||
* @var float|int
|
||||
*/
|
||||
protected $default = 60;
|
||||
|
||||
@@ -50,58 +59,6 @@ class Repository implements CacheContract, ArrayAccess
|
||||
$this->store = $store;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the event dispatcher instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Events\Dispatcher $events
|
||||
* @return void
|
||||
*/
|
||||
public function setEventDispatcher(Dispatcher $events)
|
||||
{
|
||||
$this->events = $events;
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire an event for this cache instance.
|
||||
*
|
||||
* @param string $event
|
||||
* @param array $payload
|
||||
* @return void
|
||||
*/
|
||||
protected function fireCacheEvent($event, $payload)
|
||||
{
|
||||
if (! isset($this->events)) {
|
||||
return;
|
||||
}
|
||||
|
||||
switch ($event) {
|
||||
case 'hit':
|
||||
if (count($payload) == 2) {
|
||||
$payload[] = [];
|
||||
}
|
||||
|
||||
return $this->events->fire(new Events\CacheHit($payload[0], $payload[1], $payload[2]));
|
||||
case 'missed':
|
||||
if (count($payload) == 1) {
|
||||
$payload[] = [];
|
||||
}
|
||||
|
||||
return $this->events->fire(new Events\CacheMissed($payload[0], $payload[1]));
|
||||
case 'delete':
|
||||
if (count($payload) == 1) {
|
||||
$payload[] = [];
|
||||
}
|
||||
|
||||
return $this->events->fire(new Events\KeyForgotten($payload[0], $payload[1]));
|
||||
case 'write':
|
||||
if (count($payload) == 3) {
|
||||
$payload[] = [];
|
||||
}
|
||||
|
||||
return $this->events->fire(new Events\KeyWritten($payload[0], $payload[1], $payload[2], $payload[3]));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if an item exists in the cache.
|
||||
*
|
||||
@@ -128,12 +85,15 @@ class Repository implements CacheContract, ArrayAccess
|
||||
|
||||
$value = $this->store->get($this->itemKey($key));
|
||||
|
||||
// If we could not find the cache value, we will fire the missed event and get
|
||||
// the default value for this cache value. This default could be a callback
|
||||
// so we will execute the value function which will resolve it if needed.
|
||||
if (is_null($value)) {
|
||||
$this->fireCacheEvent('missed', [$key]);
|
||||
$this->event(new CacheMissed($key));
|
||||
|
||||
$value = value($default);
|
||||
} else {
|
||||
$this->fireCacheEvent('hit', [$key, $value]);
|
||||
$this->event(new CacheHit($key, $value));
|
||||
}
|
||||
|
||||
return $value;
|
||||
@@ -149,25 +109,58 @@ class Repository implements CacheContract, ArrayAccess
|
||||
*/
|
||||
public function many(array $keys)
|
||||
{
|
||||
$normalizedKeys = [];
|
||||
$values = $this->store->many(collect($keys)->map(function ($value, $key) {
|
||||
return is_string($key) ? $key : $value;
|
||||
})->values()->all());
|
||||
|
||||
foreach ($keys as $key => $value) {
|
||||
$normalizedKeys[] = is_string($key) ? $key : $value;
|
||||
return collect($values)->map(function ($value, $key) use ($keys) {
|
||||
return $this->handleManyResult($keys, $key, $value);
|
||||
})->all();
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function getMultiple($keys, $default = null)
|
||||
{
|
||||
if (is_null($default)) {
|
||||
return $this->many($keys);
|
||||
}
|
||||
|
||||
$values = $this->store->many($normalizedKeys);
|
||||
|
||||
foreach ($values as $key => &$value) {
|
||||
if (is_null($value)) {
|
||||
$this->fireCacheEvent('missed', [$key]);
|
||||
|
||||
$value = isset($keys[$key]) ? value($keys[$key]) : null;
|
||||
} else {
|
||||
$this->fireCacheEvent('hit', [$key, $value]);
|
||||
foreach ($keys as $key) {
|
||||
if (! isset($default[$key])) {
|
||||
$default[$key] = null;
|
||||
}
|
||||
}
|
||||
|
||||
return $values;
|
||||
return $this->many($default);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle a result for the "many" method.
|
||||
*
|
||||
* @param array $keys
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @return mixed
|
||||
*/
|
||||
protected function handleManyResult($keys, $key, $value)
|
||||
{
|
||||
// If we could not find the cache value, we will fire the missed event and get
|
||||
// the default value for this cache value. This default could be a callback
|
||||
// so we will execute the value function which will resolve it if needed.
|
||||
if (is_null($value)) {
|
||||
$this->event(new CacheMissed($key));
|
||||
|
||||
return isset($keys[$key]) ? value($keys[$key]) : null;
|
||||
}
|
||||
|
||||
// If we found a valid value we will fire the "hit" event and return the value
|
||||
// back from this function. The "hit" event gives developers an opportunity
|
||||
// to listen for every possible cache "hit" throughout this applications.
|
||||
$this->event(new CacheHit($key, $value));
|
||||
|
||||
return $value;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -179,11 +172,9 @@ class Repository implements CacheContract, ArrayAccess
|
||||
*/
|
||||
public function pull($key, $default = null)
|
||||
{
|
||||
$value = $this->get($key, $default);
|
||||
|
||||
$this->forget($key);
|
||||
|
||||
return $value;
|
||||
return tap($this->get($key, $default), function ($value) use ($key) {
|
||||
$this->forget($key);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -191,64 +182,82 @@ class Repository implements CacheContract, ArrayAccess
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param \DateTime|int $minutes
|
||||
* @param \DateTimeInterface|\DateInterval|float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function put($key, $value, $minutes = null)
|
||||
{
|
||||
if (is_array($key) && filter_var($value, FILTER_VALIDATE_INT) !== false) {
|
||||
if (is_array($key)) {
|
||||
return $this->putMany($key, $value);
|
||||
}
|
||||
|
||||
$minutes = $this->getMinutes($minutes);
|
||||
|
||||
if (! is_null($minutes)) {
|
||||
if (! is_null($minutes = $this->getMinutes($minutes))) {
|
||||
$this->store->put($this->itemKey($key), $value, $minutes);
|
||||
|
||||
$this->fireCacheEvent('write', [$key, $value, $minutes]);
|
||||
$this->event(new KeyWritten($key, $value, $minutes));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function set($key, $value, $ttl = null)
|
||||
{
|
||||
$this->put($key, $value, $ttl);
|
||||
}
|
||||
|
||||
/**
|
||||
* Store multiple items in the cache for a given number of minutes.
|
||||
*
|
||||
* @param array $values
|
||||
* @param int $minutes
|
||||
* @param \DateTimeInterface|\DateInterval|float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function putMany(array $values, $minutes)
|
||||
{
|
||||
$minutes = $this->getMinutes($minutes);
|
||||
|
||||
if (! is_null($minutes)) {
|
||||
if (! is_null($minutes = $this->getMinutes($minutes))) {
|
||||
$this->store->putMany($values, $minutes);
|
||||
|
||||
foreach ($values as $key => $value) {
|
||||
$this->fireCacheEvent('write', [$key, $value, $minutes]);
|
||||
$this->event(new KeyWritten($key, $value, $minutes));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function setMultiple($values, $ttl = null)
|
||||
{
|
||||
$this->putMany($values, $ttl);
|
||||
}
|
||||
|
||||
/**
|
||||
* Store an item in the cache if the key does not exist.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @param \DateTime|int $minutes
|
||||
* @param \DateTimeInterface|\DateInterval|float|int $minutes
|
||||
* @return bool
|
||||
*/
|
||||
public function add($key, $value, $minutes)
|
||||
{
|
||||
$minutes = $this->getMinutes($minutes);
|
||||
|
||||
if (is_null($minutes)) {
|
||||
if (is_null($minutes = $this->getMinutes($minutes))) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// If the store has an "add" method we will call the method on the store so it
|
||||
// has a chance to override this logic. Some drivers better support the way
|
||||
// this operation should work with a total "atomic" implementation of it.
|
||||
if (method_exists($this->store, 'add')) {
|
||||
return $this->store->add($this->itemKey($key), $value, $minutes);
|
||||
return $this->store->add(
|
||||
$this->itemKey($key), $value, $minutes
|
||||
);
|
||||
}
|
||||
|
||||
// If the value did not exist in the cache, we will put the value in the cache
|
||||
// so it exists for subsequent requests. Then, we will return true so it is
|
||||
// easy to know if the value gets added. Otherwise, we will return false.
|
||||
if (is_null($this->get($key))) {
|
||||
$this->put($key, $value, $minutes);
|
||||
|
||||
@@ -258,6 +267,30 @@ class Repository implements CacheContract, ArrayAccess
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Increment the value of an item in the cache.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @return int|bool
|
||||
*/
|
||||
public function increment($key, $value = 1)
|
||||
{
|
||||
return $this->store->increment($key, $value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Decrement the value of an item in the cache.
|
||||
*
|
||||
* @param string $key
|
||||
* @param mixed $value
|
||||
* @return int|bool
|
||||
*/
|
||||
public function decrement($key, $value = 1)
|
||||
{
|
||||
return $this->store->decrement($key, $value);
|
||||
}
|
||||
|
||||
/**
|
||||
* Store an item in the cache indefinitely.
|
||||
*
|
||||
@@ -269,23 +302,25 @@ class Repository implements CacheContract, ArrayAccess
|
||||
{
|
||||
$this->store->forever($this->itemKey($key), $value);
|
||||
|
||||
$this->fireCacheEvent('write', [$key, $value, 0]);
|
||||
$this->event(new KeyWritten($key, $value, 0));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get an item from the cache, or store the default value.
|
||||
*
|
||||
* @param string $key
|
||||
* @param \DateTime|int $minutes
|
||||
* @param \DateTimeInterface|\DateInterval|float|int $minutes
|
||||
* @param \Closure $callback
|
||||
* @return mixed
|
||||
*/
|
||||
public function remember($key, $minutes, Closure $callback)
|
||||
{
|
||||
// If the item exists in the cache we will just return this immediately
|
||||
// otherwise we will execute the given Closure and cache the result
|
||||
// of that execution for the given number of minutes in storage.
|
||||
if (! is_null($value = $this->get($key))) {
|
||||
$value = $this->get($key);
|
||||
|
||||
// If the item exists in the cache we will just return this immediately and if
|
||||
// not we will execute the given Closure and cache the result of that for a
|
||||
// given number of minutes so it's available for all subsequent requests.
|
||||
if (! is_null($value)) {
|
||||
return $value;
|
||||
}
|
||||
|
||||
@@ -315,10 +350,12 @@ class Repository implements CacheContract, ArrayAccess
|
||||
*/
|
||||
public function rememberForever($key, Closure $callback)
|
||||
{
|
||||
// If the item exists in the cache we will just return this immediately
|
||||
// otherwise we will execute the given Closure and cache the result
|
||||
// of that execution for the given number of minutes. It's easy.
|
||||
if (! is_null($value = $this->get($key))) {
|
||||
$value = $this->get($key);
|
||||
|
||||
// If the item exists in the cache we will just return this immediately and if
|
||||
// not we will execute the given Closure and cache the result of that for a
|
||||
// given number of minutes so it's available for all subsequent requests.
|
||||
if (! is_null($value)) {
|
||||
return $value;
|
||||
}
|
||||
|
||||
@@ -330,16 +367,42 @@ class Repository implements CacheContract, ArrayAccess
|
||||
/**
|
||||
* Remove an item from the cache.
|
||||
*
|
||||
* @param string $key
|
||||
* @param string $key
|
||||
* @return bool
|
||||
*/
|
||||
public function forget($key)
|
||||
{
|
||||
$success = $this->store->forget($this->itemKey($key));
|
||||
return tap($this->store->forget($this->itemKey($key)), function () use ($key) {
|
||||
$this->event(new KeyForgotten($key));
|
||||
});
|
||||
}
|
||||
|
||||
$this->fireCacheEvent('delete', [$key]);
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function delete($key)
|
||||
{
|
||||
return $this->forget($key);
|
||||
}
|
||||
|
||||
return $success;
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function deleteMultiple($keys)
|
||||
{
|
||||
foreach ($keys as $key) {
|
||||
$this->forget($key);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function clear()
|
||||
{
|
||||
return $this->store->flush();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -352,19 +415,17 @@ class Repository implements CacheContract, ArrayAccess
|
||||
*/
|
||||
public function tags($names)
|
||||
{
|
||||
if (method_exists($this->store, 'tags')) {
|
||||
$taggedCache = $this->store->tags($names);
|
||||
|
||||
if (! is_null($this->events)) {
|
||||
$taggedCache->setEventDispatcher($this->events);
|
||||
}
|
||||
|
||||
$taggedCache->setDefaultCacheTime($this->default);
|
||||
|
||||
return $taggedCache;
|
||||
if (! method_exists($this->store, 'tags')) {
|
||||
throw new BadMethodCallException('This cache store does not support tagging.');
|
||||
}
|
||||
|
||||
throw new BadMethodCallException('This cache store does not support tagging.');
|
||||
$cache = $this->store->tags($names);
|
||||
|
||||
if (! is_null($this->events)) {
|
||||
$cache->setEventDispatcher($this->events);
|
||||
}
|
||||
|
||||
return $cache->setDefaultCacheTime($this->default);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -381,7 +442,7 @@ class Repository implements CacheContract, ArrayAccess
|
||||
/**
|
||||
* Get the default cache time.
|
||||
*
|
||||
* @return int
|
||||
* @return float|int
|
||||
*/
|
||||
public function getDefaultCacheTime()
|
||||
{
|
||||
@@ -391,12 +452,14 @@ class Repository implements CacheContract, ArrayAccess
|
||||
/**
|
||||
* Set the default cache time in minutes.
|
||||
*
|
||||
* @param int $minutes
|
||||
* @return void
|
||||
* @param float|int $minutes
|
||||
* @return $this
|
||||
*/
|
||||
public function setDefaultCacheTime($minutes)
|
||||
{
|
||||
$this->default = $minutes;
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -409,6 +472,30 @@ class Repository implements CacheContract, ArrayAccess
|
||||
return $this->store;
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire an event for this cache instance.
|
||||
*
|
||||
* @param string $event
|
||||
* @return void
|
||||
*/
|
||||
protected function event($event)
|
||||
{
|
||||
if (isset($this->events)) {
|
||||
$this->events->dispatch($event);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the event dispatcher instance.
|
||||
*
|
||||
* @param \Illuminate\Contracts\Events\Dispatcher $events
|
||||
* @return void
|
||||
*/
|
||||
public function setEventDispatcher(Dispatcher $events)
|
||||
{
|
||||
$this->events = $events;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if a cached value exists.
|
||||
*
|
||||
@@ -457,18 +544,18 @@ class Repository implements CacheContract, ArrayAccess
|
||||
/**
|
||||
* Calculate the number of minutes with the given duration.
|
||||
*
|
||||
* @param \DateTime|int $duration
|
||||
* @return int|null
|
||||
* @param \DateTimeInterface|\DateInterval|float|int $duration
|
||||
* @return float|int|null
|
||||
*/
|
||||
protected function getMinutes($duration)
|
||||
{
|
||||
if ($duration instanceof DateTime) {
|
||||
$fromNow = Carbon::now()->diffInMinutes(Carbon::instance($duration), false);
|
||||
$duration = $this->parseDateInterval($duration);
|
||||
|
||||
return $fromNow > 0 ? $fromNow : null;
|
||||
if ($duration instanceof DateTimeInterface) {
|
||||
$duration = Carbon::now()->diffInSeconds(Carbon::createFromTimestamp($duration->getTimestamp()), false) / 60;
|
||||
}
|
||||
|
||||
return is_string($duration) ? (int) $duration : $duration;
|
||||
return (int) ($duration * 60) > 0 ? $duration : null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -484,7 +571,7 @@ class Repository implements CacheContract, ArrayAccess
|
||||
return $this->macroCall($method, $parameters);
|
||||
}
|
||||
|
||||
return call_user_func_array([$this->store, $method], $parameters);
|
||||
return $this->store->$method(...$parameters);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@@ -27,7 +27,7 @@ trait RetrievesMultipleKeys
|
||||
* Store multiple items in the cache for a given number of minutes.
|
||||
*
|
||||
* @param array $values
|
||||
* @param int $minutes
|
||||
* @param float|int $minutes
|
||||
* @return void
|
||||
*/
|
||||
public function putMany(array $values, $minutes)
|
||||
|
@@ -44,24 +44,16 @@ class TagSet
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the unique tag identifier for a given tag.
|
||||
* Reset the tag and return the new tag identifier.
|
||||
*
|
||||
* @param string $name
|
||||
* @return string
|
||||
*/
|
||||
public function tagId($name)
|
||||
public function resetTag($name)
|
||||
{
|
||||
return $this->store->get($this->tagKey($name)) ?: $this->resetTag($name);
|
||||
}
|
||||
$this->store->forever($this->tagKey($name), $id = str_replace('.', '', uniqid('', true)));
|
||||
|
||||
/**
|
||||
* Get an array of tag identifiers for all of the tags in the set.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
protected function tagIds()
|
||||
{
|
||||
return array_map([$this, 'tagId'], $this->names);
|
||||
return $id;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -75,16 +67,24 @@ class TagSet
|
||||
}
|
||||
|
||||
/**
|
||||
* Reset the tag and return the new tag identifier.
|
||||
* Get an array of tag identifiers for all of the tags in the set.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
protected function tagIds()
|
||||
{
|
||||
return array_map([$this, 'tagId'], $this->names);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the unique tag identifier for a given tag.
|
||||
*
|
||||
* @param string $name
|
||||
* @return string
|
||||
*/
|
||||
public function resetTag($name)
|
||||
public function tagId($name)
|
||||
{
|
||||
$this->store->forever($this->tagKey($name), $id = str_replace('.', '', uniqid('', true)));
|
||||
|
||||
return $id;
|
||||
return $this->store->get($this->tagKey($name)) ?: $this->resetTag($name);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@@ -29,16 +29,6 @@ class TaggedCache extends Repository
|
||||
$this->tags = $tags;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected function fireCacheEvent($event, $payload)
|
||||
{
|
||||
$payload[] = $this->tags->getNames();
|
||||
|
||||
parent::fireCacheEvent($event, $payload);
|
||||
}
|
||||
|
||||
/**
|
||||
* Increment the value of an item in the cache.
|
||||
*
|
||||
@@ -91,4 +81,15 @@ class TaggedCache extends Repository
|
||||
{
|
||||
return sha1($this->tags->getNamespace()).':'.$key;
|
||||
}
|
||||
|
||||
/**
|
||||
* Fire an event for this cache instance.
|
||||
*
|
||||
* @param string $event
|
||||
* @return void
|
||||
*/
|
||||
protected function event($event)
|
||||
{
|
||||
parent::event($event->setTags($this->tags->getNames()));
|
||||
}
|
||||
}
|
||||
|
@@ -2,7 +2,7 @@
|
||||
"name": "illuminate/cache",
|
||||
"description": "The Illuminate Cache package.",
|
||||
"license": "MIT",
|
||||
"homepage": "http://laravel.com",
|
||||
"homepage": "https://laravel.com",
|
||||
"support": {
|
||||
"issues": "https://github.com/laravel/framework/issues",
|
||||
"source": "https://github.com/laravel/framework"
|
||||
@@ -14,10 +14,9 @@
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=5.5.9",
|
||||
"illuminate/contracts": "5.2.*",
|
||||
"illuminate/support": "5.2.*",
|
||||
"nesbot/carbon": "~1.20"
|
||||
"php": ">=7.0",
|
||||
"illuminate/contracts": "5.5.*",
|
||||
"illuminate/support": "5.5.*"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
@@ -26,13 +25,16 @@
|
||||
},
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "5.2-dev"
|
||||
"dev-master": "5.5-dev"
|
||||
}
|
||||
},
|
||||
"suggest": {
|
||||
"illuminate/database": "Required to use the database cache driver (5.2.*).",
|
||||
"illuminate/filesystem": "Required to use the file cache driver (5.2.*).",
|
||||
"illuminate/redis": "Required to use the redis cache driver (5.2.*)."
|
||||
"illuminate/database": "Required to use the database cache driver (5.5.*).",
|
||||
"illuminate/filesystem": "Required to use the file cache driver (5.5.*).",
|
||||
"illuminate/redis": "Required to use the redis cache driver (5.5.*)."
|
||||
},
|
||||
"config": {
|
||||
"sort-packages": true
|
||||
},
|
||||
"minimum-stability": "dev"
|
||||
}
|
||||
|
@@ -40,15 +40,40 @@ class Repository implements ArrayAccess, ConfigContract
|
||||
/**
|
||||
* Get the specified configuration value.
|
||||
*
|
||||
* @param string $key
|
||||
* @param array|string $key
|
||||
* @param mixed $default
|
||||
* @return mixed
|
||||
*/
|
||||
public function get($key, $default = null)
|
||||
{
|
||||
if (is_array($key)) {
|
||||
return $this->getMany($key);
|
||||
}
|
||||
|
||||
return Arr::get($this->items, $key, $default);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get many configuration values.
|
||||
*
|
||||
* @param array $keys
|
||||
* @return array
|
||||
*/
|
||||
public function getMany($keys)
|
||||
{
|
||||
$config = [];
|
||||
|
||||
foreach ($keys as $key => $default) {
|
||||
if (is_numeric($key)) {
|
||||
list($key, $default) = [$default, null];
|
||||
}
|
||||
|
||||
$config[$key] = Arr::get($this->items, $key, $default);
|
||||
}
|
||||
|
||||
return $config;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set a given configuration value.
|
||||
*
|
||||
@@ -58,11 +83,9 @@ class Repository implements ArrayAccess, ConfigContract
|
||||
*/
|
||||
public function set($key, $value = null)
|
||||
{
|
||||
if (is_array($key)) {
|
||||
foreach ($key as $innerKey => $innerValue) {
|
||||
Arr::set($this->items, $innerKey, $innerValue);
|
||||
}
|
||||
} else {
|
||||
$keys = is_array($key) ? $key : [$key => $value];
|
||||
|
||||
foreach ($keys as $key => $value) {
|
||||
Arr::set($this->items, $key, $value);
|
||||
}
|
||||
}
|
||||
|
@@ -2,7 +2,7 @@
|
||||
"name": "illuminate/config",
|
||||
"description": "The Illuminate Config package.",
|
||||
"license": "MIT",
|
||||
"homepage": "http://laravel.com",
|
||||
"homepage": "https://laravel.com",
|
||||
"support": {
|
||||
"issues": "https://github.com/laravel/framework/issues",
|
||||
"source": "https://github.com/laravel/framework"
|
||||
@@ -14,10 +14,9 @@
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"php": ">=5.5.9",
|
||||
"illuminate/contracts": "5.2.*",
|
||||
"illuminate/filesystem": "5.2.*",
|
||||
"illuminate/support": "5.2.*"
|
||||
"php": ">=7.0",
|
||||
"illuminate/contracts": "5.5.*",
|
||||
"illuminate/support": "5.5.*"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
@@ -26,8 +25,11 @@
|
||||
},
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "5.2-dev"
|
||||
"dev-master": "5.5-dev"
|
||||
}
|
||||
},
|
||||
"config": {
|
||||
"sort-packages": true
|
||||
},
|
||||
"minimum-stability": "dev"
|
||||
}
|
||||
|
@@ -2,11 +2,18 @@
|
||||
|
||||
namespace Illuminate\Console;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Support\ProcessUtils;
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
use Illuminate\Contracts\Container\Container;
|
||||
use Symfony\Component\Console\Input\ArgvInput;
|
||||
use Symfony\Component\Console\Input\ArrayInput;
|
||||
use Symfony\Component\Console\Input\InputOption;
|
||||
use Symfony\Component\Process\PhpExecutableFinder;
|
||||
use Symfony\Component\Console\Input\InputInterface;
|
||||
use Symfony\Component\Console\Output\ConsoleOutput;
|
||||
use Symfony\Component\Console\Output\BufferedOutput;
|
||||
use Symfony\Component\Console\Output\OutputInterface;
|
||||
use Symfony\Component\Console\Application as SymfonyApplication;
|
||||
use Symfony\Component\Console\Command\Command as SymfonyCommand;
|
||||
use Illuminate\Contracts\Console\Application as ApplicationContract;
|
||||
@@ -27,6 +34,20 @@ class Application extends SymfonyApplication implements ApplicationContract
|
||||
*/
|
||||
protected $lastOutput;
|
||||
|
||||
/**
|
||||
* The console application bootstrappers.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected static $bootstrappers = [];
|
||||
|
||||
/**
|
||||
* The Event Dispatcher.
|
||||
*
|
||||
* @var \Illuminate\Contracts\Events\Dispatcher
|
||||
*/
|
||||
protected $events;
|
||||
|
||||
/**
|
||||
* Create a new Artisan console application.
|
||||
*
|
||||
@@ -40,10 +61,101 @@ class Application extends SymfonyApplication implements ApplicationContract
|
||||
parent::__construct('Laravel Framework', $version);
|
||||
|
||||
$this->laravel = $laravel;
|
||||
$this->events = $events;
|
||||
$this->setAutoExit(false);
|
||||
$this->setCatchExceptions(false);
|
||||
|
||||
$events->fire(new Events\ArtisanStarting($this));
|
||||
$this->events->dispatch(new Events\ArtisanStarting($this));
|
||||
|
||||
$this->bootstrap();
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function run(InputInterface $input = null, OutputInterface $output = null)
|
||||
{
|
||||
$commandName = $this->getCommandName(
|
||||
$input = $input ?: new ArgvInput
|
||||
);
|
||||
|
||||
$this->events->fire(
|
||||
new Events\CommandStarting(
|
||||
$commandName, $input, $output = $output ?: new ConsoleOutput
|
||||
)
|
||||
);
|
||||
|
||||
$exitCode = parent::run($input, $output);
|
||||
|
||||
$this->events->fire(
|
||||
new Events\CommandFinished($commandName, $input, $output, $exitCode)
|
||||
);
|
||||
|
||||
return $exitCode;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine the proper PHP executable.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public static function phpBinary()
|
||||
{
|
||||
return ProcessUtils::escapeArgument((new PhpExecutableFinder)->find(false));
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine the proper Artisan executable.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
public static function artisanBinary()
|
||||
{
|
||||
return defined('ARTISAN_BINARY') ? ProcessUtils::escapeArgument(ARTISAN_BINARY) : 'artisan';
|
||||
}
|
||||
|
||||
/**
|
||||
* Format the given command as a fully-qualified executable command.
|
||||
*
|
||||
* @param string $string
|
||||
* @return string
|
||||
*/
|
||||
public static function formatCommandString($string)
|
||||
{
|
||||
return sprintf('%s %s %s', static::phpBinary(), static::artisanBinary(), $string);
|
||||
}
|
||||
|
||||
/**
|
||||
* Register a console "starting" bootstrapper.
|
||||
*
|
||||
* @param \Closure $callback
|
||||
* @return void
|
||||
*/
|
||||
public static function starting(Closure $callback)
|
||||
{
|
||||
static::$bootstrappers[] = $callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* Bootstrap the console application.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function bootstrap()
|
||||
{
|
||||
foreach (static::$bootstrappers as $bootstrapper) {
|
||||
$bootstrapper($this);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear the console application bootstrappers.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public static function forgetBootstrappers()
|
||||
{
|
||||
static::$bootstrappers = [];
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -51,13 +163,14 @@ class Application extends SymfonyApplication implements ApplicationContract
|
||||
*
|
||||
* @param string $command
|
||||
* @param array $parameters
|
||||
* @param \Symfony\Component\Console\Output\OutputInterface $outputBuffer
|
||||
* @return int
|
||||
*/
|
||||
public function call($command, array $parameters = [])
|
||||
public function call($command, array $parameters = [], $outputBuffer = null)
|
||||
{
|
||||
$parameters = collect($parameters)->prepend($command);
|
||||
|
||||
$this->lastOutput = new BufferedOutput;
|
||||
$this->lastOutput = $outputBuffer ?: new BufferedOutput;
|
||||
|
||||
$this->setCatchExceptions(false);
|
||||
|
||||
@@ -141,11 +254,9 @@ class Application extends SymfonyApplication implements ApplicationContract
|
||||
*/
|
||||
protected function getDefaultInputDefinition()
|
||||
{
|
||||
$definition = parent::getDefaultInputDefinition();
|
||||
|
||||
$definition->addOption($this->getEnvironmentOption());
|
||||
|
||||
return $definition;
|
||||
return tap(parent::getDefaultInputDefinition(), function ($definition) {
|
||||
$definition->addOption($this->getEnvironmentOption());
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -155,7 +266,7 @@ class Application extends SymfonyApplication implements ApplicationContract
|
||||
*/
|
||||
protected function getEnvironmentOption()
|
||||
{
|
||||
$message = 'The environment the command should run under.';
|
||||
$message = 'The environment the command should run under';
|
||||
|
||||
return new InputOption('--env', null, InputOption::VALUE_OPTIONAL, $message);
|
||||
}
|
||||
|
@@ -2,6 +2,7 @@
|
||||
|
||||
namespace Illuminate\Console;
|
||||
|
||||
use Illuminate\Support\Traits\Macroable;
|
||||
use Illuminate\Contracts\Support\Arrayable;
|
||||
use Symfony\Component\Console\Helper\Table;
|
||||
use Symfony\Component\Console\Input\ArrayInput;
|
||||
@@ -15,6 +16,8 @@ use Symfony\Component\Console\Command\Command as SymfonyCommand;
|
||||
|
||||
class Command extends SymfonyCommand
|
||||
{
|
||||
use Macroable;
|
||||
|
||||
/**
|
||||
* The Laravel application instance.
|
||||
*
|
||||
@@ -57,6 +60,13 @@ class Command extends SymfonyCommand
|
||||
*/
|
||||
protected $description;
|
||||
|
||||
/**
|
||||
* Indicates whether the command should be shown in the Artisan command list.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
protected $hidden = false;
|
||||
|
||||
/**
|
||||
* The default verbosity of output commands.
|
||||
*
|
||||
@@ -70,10 +80,10 @@ class Command extends SymfonyCommand
|
||||
* @var array
|
||||
*/
|
||||
protected $verbosityMap = [
|
||||
'v' => OutputInterface::VERBOSITY_VERBOSE,
|
||||
'vv' => OutputInterface::VERBOSITY_VERY_VERBOSE,
|
||||
'vvv' => OutputInterface::VERBOSITY_DEBUG,
|
||||
'quiet' => OutputInterface::VERBOSITY_QUIET,
|
||||
'v' => OutputInterface::VERBOSITY_VERBOSE,
|
||||
'vv' => OutputInterface::VERBOSITY_VERY_VERBOSE,
|
||||
'vvv' => OutputInterface::VERBOSITY_DEBUG,
|
||||
'quiet' => OutputInterface::VERBOSITY_QUIET,
|
||||
'normal' => OutputInterface::VERBOSITY_NORMAL,
|
||||
];
|
||||
|
||||
@@ -93,8 +103,13 @@ class Command extends SymfonyCommand
|
||||
parent::__construct($this->name);
|
||||
}
|
||||
|
||||
// Once we have constructed the command, we'll set the description and other
|
||||
// related properties of the command. If a signature wasn't used to build
|
||||
// the command we'll set the arguments and the options on this command.
|
||||
$this->setDescription($this->description);
|
||||
|
||||
$this->setHidden($this->hidden);
|
||||
|
||||
if (! isset($this->signature)) {
|
||||
$this->specifyParameters();
|
||||
}
|
||||
@@ -109,8 +124,11 @@ class Command extends SymfonyCommand
|
||||
{
|
||||
list($name, $arguments, $options) = Parser::parse($this->signature);
|
||||
|
||||
parent::__construct($name);
|
||||
parent::__construct($this->name = $name);
|
||||
|
||||
// After parsing the signature we will spin through the arguments and options
|
||||
// and set them on this command. These will already be changed into proper
|
||||
// instances of these "InputArgument" and "InputOption" Symfony classes.
|
||||
foreach ($arguments as $argument) {
|
||||
$this->getDefinition()->addArgument($argument);
|
||||
}
|
||||
@@ -148,11 +166,9 @@ class Command extends SymfonyCommand
|
||||
*/
|
||||
public function run(InputInterface $input, OutputInterface $output)
|
||||
{
|
||||
$this->input = $input;
|
||||
|
||||
$this->output = new OutputStyle($input, $output);
|
||||
|
||||
return parent::run($input, $output);
|
||||
return parent::run(
|
||||
$this->input = $input, $this->output = new OutputStyle($input, $output)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -164,9 +180,7 @@ class Command extends SymfonyCommand
|
||||
*/
|
||||
protected function execute(InputInterface $input, OutputInterface $output)
|
||||
{
|
||||
$method = method_exists($this, 'handle') ? 'handle' : 'fire';
|
||||
|
||||
return $this->laravel->call([$this, $method]);
|
||||
return $this->laravel->call([$this, 'handle']);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -178,11 +192,11 @@ class Command extends SymfonyCommand
|
||||
*/
|
||||
public function call($command, array $arguments = [])
|
||||
{
|
||||
$instance = $this->getApplication()->find($command);
|
||||
|
||||
$arguments['command'] = $command;
|
||||
|
||||
return $instance->run(new ArrayInput($arguments), $this->output);
|
||||
return $this->getApplication()->find($command)->run(
|
||||
$this->createInputFromArguments($arguments), $this->output
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -194,11 +208,26 @@ class Command extends SymfonyCommand
|
||||
*/
|
||||
public function callSilent($command, array $arguments = [])
|
||||
{
|
||||
$instance = $this->getApplication()->find($command);
|
||||
|
||||
$arguments['command'] = $command;
|
||||
|
||||
return $instance->run(new ArrayInput($arguments), new NullOutput);
|
||||
return $this->getApplication()->find($command)->run(
|
||||
$this->createInputFromArguments($arguments), new NullOutput
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create an input instance from the given arguments.
|
||||
*
|
||||
* @param array $arguments
|
||||
* @return \Symfony\Component\Console\Input\ArrayInput
|
||||
*/
|
||||
protected function createInputFromArguments(array $arguments)
|
||||
{
|
||||
return tap(new ArrayInput($arguments), function ($input) {
|
||||
if ($input->hasParameterOption(['--no-interaction'], true)) {
|
||||
$input->setInteractive(false);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -215,7 +244,7 @@ class Command extends SymfonyCommand
|
||||
/**
|
||||
* Get the value of a command argument.
|
||||
*
|
||||
* @param string $key
|
||||
* @param string|null $key
|
||||
* @return string|array
|
||||
*/
|
||||
public function argument($key = null)
|
||||
@@ -227,6 +256,16 @@ class Command extends SymfonyCommand
|
||||
return $this->input->getArgument($key);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all of the arguments passed to the command.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
public function arguments()
|
||||
{
|
||||
return $this->argument();
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the given option is present.
|
||||
*
|
||||
@@ -253,6 +292,16 @@ class Command extends SymfonyCommand
|
||||
return $this->input->getOption($key);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all of the options passed to the command.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
public function options()
|
||||
{
|
||||
return $this->option();
|
||||
}
|
||||
|
||||
/**
|
||||
* Confirm a question with the user.
|
||||
*
|
||||
@@ -347,10 +396,11 @@ class Command extends SymfonyCommand
|
||||
*
|
||||
* @param array $headers
|
||||
* @param \Illuminate\Contracts\Support\Arrayable|array $rows
|
||||
* @param string $style
|
||||
* @param string $tableStyle
|
||||
* @param array $columnStyles
|
||||
* @return void
|
||||
*/
|
||||
public function table(array $headers, $rows, $style = 'default')
|
||||
public function table($headers, $rows, $tableStyle = 'default', array $columnStyles = [])
|
||||
{
|
||||
$table = new Table($this->output);
|
||||
|
||||
@@ -358,7 +408,13 @@ class Command extends SymfonyCommand
|
||||
$rows = $rows->toArray();
|
||||
}
|
||||
|
||||
$table->setHeaders($headers)->setRows($rows)->setStyle($style)->render();
|
||||
$table->setHeaders((array) $headers)->setRows($rows)->setStyle($tableStyle);
|
||||
|
||||
foreach ($columnStyles as $columnIndex => $columnStyle) {
|
||||
$table->setColumnStyle($columnIndex, $columnStyle);
|
||||
}
|
||||
|
||||
$table->render();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -442,6 +498,32 @@ class Command extends SymfonyCommand
|
||||
$this->line($string, 'warning', $verbosity);
|
||||
}
|
||||
|
||||
/**
|
||||
* Write a string in an alert box.
|
||||
*
|
||||
* @param string $string
|
||||
* @return void
|
||||
*/
|
||||
public function alert($string)
|
||||
{
|
||||
$this->comment(str_repeat('*', strlen($string) + 12));
|
||||
$this->comment('* '.$string.' *');
|
||||
$this->comment(str_repeat('*', strlen($string) + 12));
|
||||
|
||||
$this->output->newLine();
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the verbosity level.
|
||||
*
|
||||
* @param string|int $level
|
||||
* @return void
|
||||
*/
|
||||
protected function setVerbosity($level)
|
||||
{
|
||||
$this->verbosity = $this->parseVerbosity($level);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the verbosity level in terms of Symfony's OutputInterface level.
|
||||
*
|
||||
@@ -459,17 +541,6 @@ class Command extends SymfonyCommand
|
||||
return $level;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the verbosity level.
|
||||
*
|
||||
* @param string|int $level
|
||||
* @return void
|
||||
*/
|
||||
protected function setVerbosity($level)
|
||||
{
|
||||
$this->verbosity = $this->parseVerbosity($level);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the console command arguments.
|
||||
*
|
||||
|
@@ -9,7 +9,9 @@ trait ConfirmableTrait
|
||||
/**
|
||||
* Confirm before proceeding with the action.
|
||||
*
|
||||
* @param string $warning
|
||||
* This method only asks for confirmation in production.
|
||||
*
|
||||
* @param string $warning
|
||||
* @param \Closure|bool|null $callback
|
||||
* @return bool
|
||||
*/
|
||||
@@ -24,10 +26,7 @@ trait ConfirmableTrait
|
||||
return true;
|
||||
}
|
||||
|
||||
$this->comment(str_repeat('*', strlen($warning) + 12));
|
||||
$this->comment('* '.$warning.' *');
|
||||
$this->comment(str_repeat('*', strlen($warning) + 12));
|
||||
$this->output->writeln('');
|
||||
$this->alert($warning);
|
||||
|
||||
$confirmed = $this->confirm('Do you really wish to run this command?');
|
||||
|
||||
|
@@ -4,7 +4,7 @@ namespace Illuminate\Console;
|
||||
|
||||
use Illuminate\Container\Container;
|
||||
|
||||
trait AppNamespaceDetectorTrait
|
||||
trait DetectsApplicationNamespace
|
||||
{
|
||||
/**
|
||||
* Get the application namespace.
|
54
vendor/laravel/framework/src/Illuminate/Console/Events/CommandFinished.php
vendored
Normal file
54
vendor/laravel/framework/src/Illuminate/Console/Events/CommandFinished.php
vendored
Normal file
@@ -0,0 +1,54 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Console\Events;
|
||||
|
||||
use Symfony\Component\Console\Input\InputInterface;
|
||||
use Symfony\Component\Console\Output\OutputInterface;
|
||||
|
||||
class CommandFinished
|
||||
{
|
||||
/**
|
||||
* The command name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $command;
|
||||
|
||||
/**
|
||||
* The console input implementation.
|
||||
*
|
||||
* @var \Symfony\Component\Console\Input\InputInterface|null
|
||||
*/
|
||||
public $input;
|
||||
|
||||
/**
|
||||
* The command output implementation.
|
||||
*
|
||||
* @var \Symfony\Component\Console\Output\OutputInterface|null
|
||||
*/
|
||||
public $output;
|
||||
|
||||
/**
|
||||
* The command exit code.
|
||||
*
|
||||
* @var int
|
||||
*/
|
||||
public $exitCode;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $command
|
||||
* @param \Symfony\Component\Console\Input\InputInterface $input
|
||||
* @param \Symfony\Component\Console\Output\OutputInterface $output
|
||||
* @param int $exitCode
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($command, InputInterface $input, OutputInterface $output, $exitCode)
|
||||
{
|
||||
$this->input = $input;
|
||||
$this->output = $output;
|
||||
$this->command = $command;
|
||||
$this->exitCode = $exitCode;
|
||||
}
|
||||
}
|
45
vendor/laravel/framework/src/Illuminate/Console/Events/CommandStarting.php
vendored
Normal file
45
vendor/laravel/framework/src/Illuminate/Console/Events/CommandStarting.php
vendored
Normal file
@@ -0,0 +1,45 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Console\Events;
|
||||
|
||||
use Symfony\Component\Console\Input\InputInterface;
|
||||
use Symfony\Component\Console\Output\OutputInterface;
|
||||
|
||||
class CommandStarting
|
||||
{
|
||||
/**
|
||||
* The command name.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
public $command;
|
||||
|
||||
/**
|
||||
* The console input implementation.
|
||||
*
|
||||
* @var \Symfony\Component\Console\Input\InputInterface|null
|
||||
*/
|
||||
public $input;
|
||||
|
||||
/**
|
||||
* The command output implementation.
|
||||
*
|
||||
* @var \Symfony\Component\Console\Output\OutputInterface|null
|
||||
*/
|
||||
public $output;
|
||||
|
||||
/**
|
||||
* Create a new event instance.
|
||||
*
|
||||
* @param string $command
|
||||
* @param \Symfony\Component\Console\Input\InputInterface $input
|
||||
* @param \Symfony\Component\Console\Output\OutputInterface $output
|
||||
* @return void
|
||||
*/
|
||||
public function __construct($command, InputInterface $input, OutputInterface $output)
|
||||
{
|
||||
$this->input = $input;
|
||||
$this->output = $output;
|
||||
$this->command = $command;
|
||||
}
|
||||
}
|
@@ -47,18 +47,24 @@ abstract class GeneratorCommand extends Command
|
||||
*
|
||||
* @return bool|null
|
||||
*/
|
||||
public function fire()
|
||||
public function handle()
|
||||
{
|
||||
$name = $this->parseName($this->getNameInput());
|
||||
$name = $this->qualifyClass($this->getNameInput());
|
||||
|
||||
$path = $this->getPath($name);
|
||||
|
||||
if ($this->alreadyExists($this->getNameInput())) {
|
||||
// First we will check to see if the class already exists. If it does, we don't want
|
||||
// to create the class and overwrite the user's code. So, we will bail out so the
|
||||
// code is untouched. Otherwise, we will continue generating this class' files.
|
||||
if ((! $this->hasOption('force') || ! $this->option('force')) && $this->alreadyExists($this->getNameInput())) {
|
||||
$this->error($this->type.' already exists!');
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
// Next, we will generate the path to the location where this class' file should get
|
||||
// written. Then, we will build the class and make the proper replacements on the
|
||||
// stub files so that it gets the correctly formatted namespace and class name.
|
||||
$this->makeDirectory($path);
|
||||
|
||||
$this->files->put($path, $this->buildClass($name));
|
||||
@@ -67,50 +73,26 @@ abstract class GeneratorCommand extends Command
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the class already exists.
|
||||
*
|
||||
* @param string $rawName
|
||||
* @return bool
|
||||
*/
|
||||
protected function alreadyExists($rawName)
|
||||
{
|
||||
$name = $this->parseName($rawName);
|
||||
|
||||
return $this->files->exists($this->getPath($name));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the destination class path.
|
||||
* Parse the class name and format according to the root namespace.
|
||||
*
|
||||
* @param string $name
|
||||
* @return string
|
||||
*/
|
||||
protected function getPath($name)
|
||||
protected function qualifyClass($name)
|
||||
{
|
||||
$name = str_replace($this->laravel->getNamespace(), '', $name);
|
||||
$name = ltrim($name, '\\/');
|
||||
|
||||
return $this->laravel['path'].'/'.str_replace('\\', '/', $name).'.php';
|
||||
}
|
||||
|
||||
/**
|
||||
* Parse the name and format according to the root namespace.
|
||||
*
|
||||
* @param string $name
|
||||
* @return string
|
||||
*/
|
||||
protected function parseName($name)
|
||||
{
|
||||
$rootNamespace = $this->laravel->getNamespace();
|
||||
$rootNamespace = $this->rootNamespace();
|
||||
|
||||
if (Str::startsWith($name, $rootNamespace)) {
|
||||
return $name;
|
||||
}
|
||||
|
||||
if (Str::contains($name, '/')) {
|
||||
$name = str_replace('/', '\\', $name);
|
||||
}
|
||||
$name = str_replace('/', '\\', $name);
|
||||
|
||||
return $this->parseName($this->getDefaultNamespace(trim($rootNamespace, '\\')).'\\'.$name);
|
||||
return $this->qualifyClass(
|
||||
$this->getDefaultNamespace(trim($rootNamespace, '\\')).'\\'.$name
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -124,6 +106,30 @@ abstract class GeneratorCommand extends Command
|
||||
return $rootNamespace;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the class already exists.
|
||||
*
|
||||
* @param string $rawName
|
||||
* @return bool
|
||||
*/
|
||||
protected function alreadyExists($rawName)
|
||||
{
|
||||
return $this->files->exists($this->getPath($this->qualifyClass($rawName)));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the destination class path.
|
||||
*
|
||||
* @param string $name
|
||||
* @return string
|
||||
*/
|
||||
protected function getPath($name)
|
||||
{
|
||||
$name = Str::replaceFirst($this->rootNamespace(), '', $name);
|
||||
|
||||
return $this->laravel['path'].'/'.str_replace('\\', '/', $name).'.php';
|
||||
}
|
||||
|
||||
/**
|
||||
* Build the directory for the class if necessary.
|
||||
*
|
||||
@@ -135,6 +141,8 @@ abstract class GeneratorCommand extends Command
|
||||
if (! $this->files->isDirectory(dirname($path))) {
|
||||
$this->files->makeDirectory(dirname($path), 0777, true, true);
|
||||
}
|
||||
|
||||
return $path;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -160,18 +168,16 @@ abstract class GeneratorCommand extends Command
|
||||
protected function replaceNamespace(&$stub, $name)
|
||||
{
|
||||
$stub = str_replace(
|
||||
'DummyNamespace', $this->getNamespace($name), $stub
|
||||
);
|
||||
|
||||
$stub = str_replace(
|
||||
'DummyRootNamespace', $this->laravel->getNamespace(), $stub
|
||||
['DummyNamespace', 'DummyRootNamespace', 'NamespacedDummyUserModel'],
|
||||
[$this->getNamespace($name), $this->rootNamespace(), config('auth.providers.users.model')],
|
||||
$stub
|
||||
);
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the full namespace name for a given class.
|
||||
* Get the full namespace for a given class, without the class name.
|
||||
*
|
||||
* @param string $name
|
||||
* @return string
|
||||
@@ -205,6 +211,16 @@ abstract class GeneratorCommand extends Command
|
||||
return trim($this->argument('name'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the root namespace for the class.
|
||||
*
|
||||
* @return string
|
||||
*/
|
||||
protected function rootNamespace()
|
||||
{
|
||||
return $this->laravel->getNamespace();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the console command arguments.
|
||||
*
|
||||
|
@@ -18,28 +18,35 @@ class Parser
|
||||
* @throws \InvalidArgumentException
|
||||
*/
|
||||
public static function parse($expression)
|
||||
{
|
||||
$name = static::name($expression);
|
||||
|
||||
if (preg_match_all('/\{\s*(.*?)\s*\}/', $expression, $matches)) {
|
||||
if (count($matches[1])) {
|
||||
return array_merge([$name], static::parameters($matches[1]));
|
||||
}
|
||||
}
|
||||
|
||||
return [$name, [], []];
|
||||
}
|
||||
|
||||
/**
|
||||
* Extract the name of the command from the expression.
|
||||
*
|
||||
* @param string $expression
|
||||
* @return string
|
||||
*/
|
||||
protected static function name($expression)
|
||||
{
|
||||
if (trim($expression) === '') {
|
||||
throw new InvalidArgumentException('Console command definition is empty.');
|
||||
}
|
||||
|
||||
preg_match('/[^\s]+/', $expression, $matches);
|
||||
|
||||
if (isset($matches[0])) {
|
||||
$name = $matches[0];
|
||||
} else {
|
||||
if (! preg_match('/[^\s]+/', $expression, $matches)) {
|
||||
throw new InvalidArgumentException('Unable to determine command name from signature.');
|
||||
}
|
||||
|
||||
preg_match_all('/\{\s*(.*?)\s*\}/', $expression, $matches);
|
||||
|
||||
$tokens = isset($matches[1]) ? $matches[1] : [];
|
||||
|
||||
if (count($tokens)) {
|
||||
return array_merge([$name], static::parameters($tokens));
|
||||
}
|
||||
|
||||
return [$name, [], []];
|
||||
return $matches[0];
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -55,10 +62,10 @@ class Parser
|
||||
$options = [];
|
||||
|
||||
foreach ($tokens as $token) {
|
||||
if (! Str::startsWith($token, '--')) {
|
||||
$arguments[] = static::parseArgument($token);
|
||||
if (preg_match('/-{2,}(.*)/', $token, $matches)) {
|
||||
$options[] = static::parseOption($matches[1]);
|
||||
} else {
|
||||
$options[] = static::parseOption(ltrim($token, '-'));
|
||||
$arguments[] = static::parseArgument($token);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -73,15 +80,7 @@ class Parser
|
||||
*/
|
||||
protected static function parseArgument($token)
|
||||
{
|
||||
$description = null;
|
||||
|
||||
if (Str::contains($token, ' : ')) {
|
||||
list($token, $description) = explode(' : ', $token, 2);
|
||||
|
||||
$token = trim($token);
|
||||
|
||||
$description = trim($description);
|
||||
}
|
||||
list($token, $description) = static::extractDescription($token);
|
||||
|
||||
switch (true) {
|
||||
case Str::endsWith($token, '?*'):
|
||||
@@ -90,6 +89,8 @@ class Parser
|
||||
return new InputArgument(trim($token, '*'), InputArgument::IS_ARRAY | InputArgument::REQUIRED, $description);
|
||||
case Str::endsWith($token, '?'):
|
||||
return new InputArgument(trim($token, '?'), InputArgument::OPTIONAL, $description);
|
||||
case preg_match('/(.+)\=\*(.+)/', $token, $matches):
|
||||
return new InputArgument($matches[1], InputArgument::IS_ARRAY, $description, preg_split('/,\s?/', $matches[2]));
|
||||
case preg_match('/(.+)\=(.+)/', $token, $matches):
|
||||
return new InputArgument($matches[1], InputArgument::OPTIONAL, $description, $matches[2]);
|
||||
default:
|
||||
@@ -105,21 +106,15 @@ class Parser
|
||||
*/
|
||||
protected static function parseOption($token)
|
||||
{
|
||||
$description = null;
|
||||
|
||||
if (Str::contains($token, ' : ')) {
|
||||
list($token, $description) = explode(' : ', $token);
|
||||
$token = trim($token);
|
||||
$description = trim($description);
|
||||
}
|
||||
|
||||
$shortcut = null;
|
||||
list($token, $description) = static::extractDescription($token);
|
||||
|
||||
$matches = preg_split('/\s*\|\s*/', $token, 2);
|
||||
|
||||
if (isset($matches[1])) {
|
||||
$shortcut = $matches[0];
|
||||
$token = $matches[1];
|
||||
} else {
|
||||
$shortcut = null;
|
||||
}
|
||||
|
||||
switch (true) {
|
||||
@@ -127,10 +122,25 @@ class Parser
|
||||
return new InputOption(trim($token, '='), $shortcut, InputOption::VALUE_OPTIONAL, $description);
|
||||
case Str::endsWith($token, '=*'):
|
||||
return new InputOption(trim($token, '=*'), $shortcut, InputOption::VALUE_OPTIONAL | InputOption::VALUE_IS_ARRAY, $description);
|
||||
case preg_match('/(.+)\=\*(.+)/', $token, $matches):
|
||||
return new InputOption($matches[1], $shortcut, InputOption::VALUE_OPTIONAL | InputOption::VALUE_IS_ARRAY, $description, preg_split('/,\s?/', $matches[2]));
|
||||
case preg_match('/(.+)\=(.+)/', $token, $matches):
|
||||
return new InputOption($matches[1], $shortcut, InputOption::VALUE_OPTIONAL, $description, $matches[2]);
|
||||
default:
|
||||
return new InputOption($token, $shortcut, InputOption::VALUE_NONE, $description);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Parse the token into its token and description segments.
|
||||
*
|
||||
* @param string $token
|
||||
* @return array
|
||||
*/
|
||||
protected static function extractDescription($token)
|
||||
{
|
||||
$parts = preg_split('/\s+:\s+/', trim($token), 2);
|
||||
|
||||
return count($parts) === 2 ? $parts : [$token, ''];
|
||||
}
|
||||
}
|
||||
|
@@ -1,37 +0,0 @@
|
||||
<?php
|
||||
|
||||
namespace Illuminate\Console;
|
||||
|
||||
use Illuminate\Support\ServiceProvider;
|
||||
|
||||
class ScheduleServiceProvider extends ServiceProvider
|
||||
{
|
||||
/**
|
||||
* Indicates if loading of the provider is deferred.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
protected $defer = true;
|
||||
|
||||
/**
|
||||
* Register the service provider.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function register()
|
||||
{
|
||||
$this->commands('Illuminate\Console\Scheduling\ScheduleRunCommand');
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the services provided by the provider.
|
||||
*
|
||||
* @return array
|
||||
*/
|
||||
public function provides()
|
||||
{
|
||||
return [
|
||||
'Illuminate\Console\Scheduling\ScheduleRunCommand',
|
||||
];
|
||||
}
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user