From 5cbb66fdf2ba5b53ced065241ee0e312ac0d6028 Mon Sep 17 00:00:00 2001 From: cexbrayat Date: Sat, 10 Jan 2026 10:50:19 +0100 Subject: [PATCH] test(forms): improve test coverage for multiple pattern validators Add comprehensive test cases to validate behavior when multiple pattern validators are applied to the same field. These tests clarify that multiple patterns operate with AND logic, where each pattern is validated independently and produces its own error when it doesn't match. (cherry picked from commit 7fd076bdd329071d8705acc5de9a852cbc68ab60) --- .../test/node/api/validators/pattern.spec.ts | 51 +++++++++++++++++++ 1 file changed, 51 insertions(+) diff --git a/packages/forms/signals/test/node/api/validators/pattern.spec.ts b/packages/forms/signals/test/node/api/validators/pattern.spec.ts index 13f884fae0c..b043eaf336e 100644 --- a/packages/forms/signals/test/node/api/validators/pattern.spec.ts +++ b/packages/forms/signals/test/node/api/validators/pattern.spec.ts @@ -95,6 +95,57 @@ describe('pattern validator', () => { expect(f.name().pattern()).toEqual([/pir.*jok/, /pelmeni/]); }); + it('validates multiple patterns independently (AND logic)', () => { + const model = signal('abc123'); + const f = form( + model, + (p) => { + pattern(p, /abc/); // matches + pattern(p, /\d+/); // matches + }, + {injector: TestBed.inject(Injector)}, + ); + + // Both patterns match, so no errors + expect(f().pattern()).toEqual([/abc/, /\d+/]); + expect(f().errors()).toEqual([]); + }); + + it('validates multiple patterns independently - partial match produces errors', () => { + const model = signal('abc'); + const f = form( + model, + (p) => { + pattern(p, /abc/); // matches + pattern(p, /\d+/); // does not match + }, + {injector: TestBed.inject(Injector)}, + ); + + // Only one pattern matches, so we get an error from the non-matching one + expect(f().pattern()).toEqual([/abc/, /\d+/]); + expect(f().errors()).toEqual([patternError(/\d+/, {fieldTree: f})]); + }); + + it('validates multiple patterns - no match produces multiple errors', () => { + const model = signal('xyz'); + const f = form( + model, + (p) => { + pattern(p, /abc/); // does not match + pattern(p, /\d+/); // does not match + }, + {injector: TestBed.inject(Injector)}, + ); + + // No patterns match, so we get errors from both + expect(f().pattern()).toEqual([/abc/, /\d+/]); + expect(f().errors()).toEqual([ + patternError(/abc/, {fieldTree: f}), + patternError(/\d+/, {fieldTree: f}), + ]); + }); + it('PATTERN property defaults to empty list', () => { const cat = signal({name: 'pelmeni-the-cat'}); const f = form(