Repository navigation
Fix validator regex alternation, array input 500s and duplicated errors - #394
Merged
techmahedy merged 1 commit intoOct 30, 2026
Merged
Conversation
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Pull Request Checklist
Description
Three bugs in the request validator (
Sanitizerand theRuletrait behind$request->sanitize()), found by running every rule against awkward input.1. A
|inside a regex rule was treated as a rule separatorBoth rule loops did
explode('|', $rules), soregex:/^(cat|dog)$/became two broken rules and could never match.cat,dogandcowall failed.splitRules()in theValidationRulestrait now keeps aregex:rule together until its closing delimiter. It handles flags (/i), other delimiters (#,~,{},()), an escaped delimiter inside the pattern, and a pattern ending in an escaped backslash. An unterminated pattern keeps its own piece and does not swallow the rules after it. BothSanitizer::validate()andRule::sanitize()use it.2. Array or object input crashed the request
A query string like
?name[]=x, or JSON like{"name":["x"]}, made 25 rules throw aTypeErrororError(or emit an "Array to string conversion" warning) instead of failing validation. Affected rules:min,max,date,gte,lte,gt,lt,alpha,alpha_num,alpha_dash,regex,phone,uuid,starts_with,ends_with,date_format,uppercase,lowercase,slug,digits,min_digits,max_digits,same_as,uniqueandexists_in. Puttingstringbeforemindid not help, because later rules still run.uniqueandexists_inalso looked up the literal string"Array"in the database.sanitizeUserRequestnow fails these fields with the "must be a string" message. Objects are rejected for every rule exceptrequired,array,stringandnull. A string containing a NUL byte now failsdate_formatinstead of throwing aValueError.On the live app,
POST /loginwithpassword[]=xreturned 500 before and 302 after (the normal redirect-back-with-errors).3. Errors piled up when validating more than once
validate()never cleared$this->errors, so callingfails()twice, orfails()thenvalidate(), listed the same message repeatedly. It now resets first. Identical messages for one field are also shown only once, which keepsrequired|string|min:3on an array to a single error.Changes
ValidationRules:splitRules(),isRegexClosed(),rejectsNonScalarValue(), the guard insanitizeUserRequest, and the NUL-byte check inisDateFormat.Sanitizer: usessplitRules(), resets errors invalidate(), de-duplicates messages inaddError().Rule: usessplitRules()and de-duplicates messages.ValidationHardeningTestwith 104 tests, including the previously untestedRule::sanitize()path.Checklist