Skip to content

Commit

Permalink
Introduce Conditional trait on validation rules
Browse files Browse the repository at this point in the history
  • Loading branch information
inxilpro committed May 27, 2021
1 parent 593f0dd commit 1808581
Show file tree
Hide file tree
Showing 9 changed files with 124 additions and 0 deletions.
45 changes: 45 additions & 0 deletions src/Illuminate/Support/Traits/Conditional.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
<?php

namespace Illuminate\Support\Traits;

use BadMethodCallException;
use Closure;
use ReflectionClass;
use ReflectionMethod;

trait Conditional
{
/**
* Apply the callback if the given "value" is true.
*
* @param mixed $value
* @param callable $callback
* @param callable|null $default
*
* @return mixed|$this
*/
public function when($value, $callback, $default = null)
{
if ($value) {
return $callback($this, $value) ?: $this;
} elseif ($default) {
return $default($this, $value) ?: $this;
}

return $this;
}

/**
* Apply the callback if the given "value" is false.
*
* @param mixed $value
* @param callable $callback
* @param callable|null $default
*
* @return mixed|$this
*/
public function unless($value, $callback, $default = null)
{
return $this->when(! $value, $callback, $default);
}
}
4 changes: 4 additions & 0 deletions src/Illuminate/Validation/Rules/Dimensions.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,12 @@

namespace Illuminate\Validation\Rules;

use Illuminate\Support\Traits\Conditional;

class Dimensions
{
use Conditional;

/**
* The constraints for the dimensions rule.
*
Expand Down
3 changes: 3 additions & 0 deletions src/Illuminate/Validation/Rules/Exists.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,12 @@

namespace Illuminate\Validation\Rules;

use Illuminate\Support\Traits\Conditional;

class Exists
{
use DatabaseRule;
use Conditional;

/**
* Convert the rule to a validation string.
Expand Down
3 changes: 3 additions & 0 deletions src/Illuminate/Validation/Rules/Password.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,13 @@
use Illuminate\Contracts\Validation\UncompromisedVerifier;
use Illuminate\Support\Arr;
use Illuminate\Support\Facades\Validator;
use Illuminate\Support\Traits\Conditional;
use InvalidArgumentException;

class Password implements Rule, DataAwareRule
{
use Conditional;

/**
* The data under validation.
*
Expand Down
2 changes: 2 additions & 0 deletions src/Illuminate/Validation/Rules/Unique.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,12 @@
namespace Illuminate\Validation\Rules;

use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Traits\Conditional;

class Unique
{
use DatabaseRule;
use Conditional;

/**
* The ID that should be ignored.
Expand Down
9 changes: 9 additions & 0 deletions tests/Validation/ValidationDimensionsRuleTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -29,5 +29,14 @@ public function testItCorrectlyFormatsAStringVersionOfTheRule()
$rule = Rule::dimensions()->minWidth(300)->minHeight(400);

$this->assertSame('dimensions:min_width=300,min_height=400', (string) $rule);

$rule = Rule::dimensions()
->when(true, function($rule) {
$rule->height('100');
})
->unless(true, function($rule) {
$rule->width('200');
});
$this->assertSame('dimensions:height=100', (string) $rule);
}
}
29 changes: 29 additions & 0 deletions tests/Validation/ValidationExistsRuleTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,35 @@ public function testItChoosesValidRecordsUsingWhereNotInRule()
$this->assertTrue($v->passes());
}

public function testItChoosesValidRecordsUsingConditionalModifiers()
{
$rule = new Exists('users', 'id');
$rule->when(true, function($rule) {
$rule->whereNotIn('type', [ 'foo', 'bar' ]);
});
$rule->unless(true, function($rule) {
$rule->whereNotIn('type', [ 'baz', 'other' ]);
});

User::create([ 'id' => '1', 'type' => 'foo' ]);
User::create([ 'id' => '2', 'type' => 'bar' ]);
User::create([ 'id' => '3', 'type' => 'baz' ]);
User::create([ 'id' => '4', 'type' => 'other' ]);

$trans = $this->getIlluminateArrayTranslator();
$v = new Validator($trans, [], [ 'id' => $rule ]);
$v->setPresenceVerifier(new DatabasePresenceVerifier(Eloquent::getConnectionResolver()));

$v->setData([ 'id' => 1 ]);
$this->assertFalse($v->passes());
$v->setData([ 'id' => 2 ]);
$this->assertFalse($v->passes());
$v->setData([ 'id' => 3 ]);
$this->assertTrue($v->passes());
$v->setData([ 'id' => 4 ]);
$this->assertTrue($v->passes());
}

public function testItChoosesValidRecordsUsingWhereNotInAndWhereNotInRulesTogether()
{
$rule = new Exists('users', 'id');
Expand Down
19 changes: 19 additions & 0 deletions tests/Validation/ValidationPasswordRuleTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,25 @@ public function testMin()
$this->passes(new Password(8), ['88888888']);
}

public function testConditional()
{
$is_privileged_user = true;
$rule = (new Password(8))->when($is_privileged_user, function($rule) {
$rule->symbols();
});

$this->fails($rule, [ 'aaaaaaaa', '11111111' ], [
'The my password must contain at least one symbol.',
]);

$is_privileged_user = false;
$rule = (new Password(8))->when($is_privileged_user, function($rule) {
$rule->symbols();
});

$this->passes($rule, [ 'aaaaaaaa', '11111111' ]);
}

public function testMixedCase()
{
$this->fails(Password::min(2)->mixedCase(), ['nn', 'MM'], [
Expand Down
10 changes: 10 additions & 0 deletions tests/Validation/ValidationUniqueRuleTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,16 @@ public function testItCorrectlyFormatsAStringVersionOfTheRule()
$rule->where('foo', 'bar');
$this->assertSame('unique:table,column,"Taylor, Otwell",id_column,foo,"bar"', (string) $rule);

$rule = new Unique(EloquentModelStub::class, 'column');
$rule->where('foo', 'bar');
$rule->when(true, function($rule) {
$rule->ignore('Taylor, Otwell', 'id_column');
});
$rule->unless(true, function($rule) {
$rule->ignore('Chris', 'id_column');
});
$this->assertSame('unique:table,column,"Taylor, Otwell",id_column,foo,"bar"', (string) $rule);

$rule = new Unique('table', 'column');
$rule->ignore('Taylor, Otwell"\'..-"', 'id_column');
$rule->where('foo', 'bar');
Expand Down

0 comments on commit 1808581

Please sign in to comment.