@@ -112,6 +112,17 @@ describe('composition validation', () => {
112112 expect ( result . valid ) . toBe ( false ) ;
113113 expect ( result . errors . some ( ( e ) => e . keyword === 'required' ) ) . toBe ( true ) ;
114114 } ) ;
115+
116+ it ( 'validates merged properties in strict mode' , ( ) => {
117+ const result = validator . validateResponse ( '/v1/users/{userId}' , 'get' , 200 , {
118+ id : 1 ,
119+ email : 'test@example.com' ,
120+ name : 'John' ,
121+ avatar : null ,
122+ } ) ;
123+ expect ( result . valid ) . toBe ( true ) ;
124+ expect ( result . errors ) . toHaveLength ( 0 ) ;
125+ } ) ;
115126 } ) ;
116127
117128 describe ( 'nullable + oneOf (3.0 normalization)' , ( ) => {
@@ -262,5 +273,36 @@ describe('composition validation', () => {
262273 expect ( result . valid ) . toBe ( true ) ;
263274 expect ( result . errors ) . toHaveLength ( 0 ) ;
264275 } ) ;
276+
277+ it ( 'still rejects invalid type value in strict mode' , ( ) => {
278+ const result = validator . validateRequest ( '/v1/cart-items' , 'post' , [
279+ {
280+ type : 'unknown' ,
281+ value : { name : 'Test' , sku : 'test' } ,
282+ } ,
283+ ] ) ;
284+ expect ( result . valid ) . toBe ( false ) ;
285+ } ) ;
286+
287+ it ( 'still rejects extra properties on the item in strict mode' , ( ) => {
288+ const result = validator . validateRequest ( '/v1/cart-items' , 'post' , [
289+ {
290+ type : 'plan' ,
291+ value : { name : 'Plan' , sku : 'plan-1' , periodicity : 'monthly' , metadata : { recurrence : 'monthly' } } ,
292+ extraField : 'should not be here' ,
293+ } ,
294+ ] ) ;
295+ expect ( result . valid ) . toBe ( false ) ;
296+ } ) ;
297+
298+ it ( 'still rejects missing required fields in strict mode' , ( ) => {
299+ const result = validator . validateRequest ( '/v1/cart-items' , 'post' , [
300+ {
301+ type : 'trip' ,
302+ value : { name : 'Spain' } ,
303+ } ,
304+ ] ) ;
305+ expect ( result . valid ) . toBe ( false ) ;
306+ } ) ;
265307 } ) ;
266308} ) ;
0 commit comments