From ad8170d1048f8a26a2d51f36ef54fe2276beba11 Mon Sep 17 00:00:00 2001 From: Tommy Leirvik Date: Sat, 30 Aug 2014 14:49:34 +0200 Subject: [PATCH] Dynamic where rules MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Allow for dynamic where rules example: 'email' => 'exists:staff,email,account_id,1' rule will be: 'email' => 'exists:staff,email,account_id,{account_id}’ via ->validate($formData, [‘account_id’ => 1]); --- .../Validation/FormValidatorSpec.php | 20 +++++++++- src/Laracasts/Validation/FormValidator.php | 40 ++++++++++++++++++- 2 files changed, 57 insertions(+), 3 deletions(-) diff --git a/spec/Laracasts/Validation/FormValidatorSpec.php b/spec/Laracasts/Validation/FormValidatorSpec.php index 3935ab8..d6d47dc 100644 --- a/spec/Laracasts/Validation/FormValidatorSpec.php +++ b/spec/Laracasts/Validation/FormValidatorSpec.php @@ -36,6 +36,20 @@ function it_throws_an_exception_for_invalid_form_data(FactoryInterface $validato $this->shouldThrow('Laracasts\Validation\FormValidationException')->duringValidate($fakeFormData); } + function it_injects_mappings_into_rules(FactoryInterface $validatorFactory, ValidatorInterface $validator) + { + $fakeFormData = ['username' => 'joe', 'email' => 'joe@example.com']; + $mappings = ['user_id' => 1]; + $convertedRuleSet = ['username' => 'required', 'email' => 'unique:users,email,1,id']; + + $validatorFactory->make($fakeFormData, $convertedRuleSet, [])->willReturn($validator); + $validator->fails()->willReturn(false); + + $this->validate($fakeFormData, $mappings)->shouldReturn(true); + + $this->getValidationRules()->shouldBe($convertedRuleSet); + } + function it_accepts_a_command_object_in_lieu_of_an_input_array(FactoryInterface $validatorFactory, ValidatorInterface $validator) { $formDataAsCommand = new CommandStub; @@ -44,12 +58,14 @@ function it_accepts_a_command_object_in_lieu_of_an_input_array(FactoryInterface $validatorFactory->make($formDataCastToArray, $this->getValidationRules(), [])->willReturn($validator); $this->validate($formDataAsCommand)->shouldReturn(true); - } } class ExampleValidator extends \Laracasts\Validation\FormValidator { - protected $rules = ['username' => 'required']; + protected $rules = [ + 'username' => 'required', + 'email' => 'unique:users,email,{user_id},id' + ]; } class CommandStub { diff --git a/src/Laracasts/Validation/FormValidator.php b/src/Laracasts/Validation/FormValidator.php index ec4fd62..ecbbd09 100644 --- a/src/Laracasts/Validation/FormValidator.php +++ b/src/Laracasts/Validation/FormValidator.php @@ -32,11 +32,17 @@ function __construct(ValidatorFactory $validator) * Validate the form data * * @param mixed $formData + * @param array $mappings * @return mixed * @throws FormValidationException */ - public function validate($formData) + public function validate($formData, $mappings = []) { + if ( ! empty($mappings)) + { + $this->replaceRulePlaceholdersWith($mappings); + } + $formData = $this->normalizeFormData($formData); $this->validation = $this->validator->make( @@ -98,4 +104,36 @@ protected function normalizeFormData($formData) return $formData; } + /** + * Go trough all the mappings + * and inject the mappings into the rules. + * + * @param array $mappings + * @return void + */ + protected function replaceRulePlaceholdersWith(array $mappings) + { + $rules = $this->getValidationRules(); + + foreach ($mappings as $search => $value) + { + $this->injectMappingIntoRules($rules, $search, $value); + } + } + + /** + * Inject a mapping into all defined rules. + * + * @param array $rules + * @param string $search + * @param mixed $value + * @return void + */ + protected function injectMappingIntoRules(array $rules, $search, $value) + { + foreach ($rules as $field => $rule) + { + $this->rules[$field] = str_replace('{'.$search.'}', $value, $rule); + } + } }