@@ -621,7 +621,7 @@ public void testNormalize31Parameters() {
621621 }
622622
623623 @ Test
624- public void testNormalize31ExclusiveMinMaxNumeric () {
624+ public void testNormalize31ExclusiveMinMaxNumericOnly () {
625625 OpenAPI openAPI = TestUtils .parseSpec ("src/test/resources/3_1/exclusive-min-max.yaml" );
626626
627627 OpenAPINormalizer n = new OpenAPINormalizer (openAPI , Map .of ("NORMALIZE_31SPEC" , "true" ));
@@ -634,13 +634,116 @@ public void testNormalize31ExclusiveMinMaxNumeric() {
634634 .get (0 )
635635 .getSchema ();
636636
637+ // exclusiveMinimum: 0
638+ assertEquals (new BigDecimal ("0" ), schema .getExclusiveMinimumValue ());
637639 assertEquals (new BigDecimal ("0" ), schema .getMinimum ());
638640 assertEquals (Boolean .TRUE , schema .getExclusiveMinimum ());
639641
642+ // exclusiveMaximum: 10
643+ assertEquals (new BigDecimal ("10" ), schema .getExclusiveMaximumValue ());
640644 assertEquals (new BigDecimal ("10" ), schema .getMaximum ());
641645 assertEquals (Boolean .TRUE , schema .getExclusiveMaximum ());
642646 }
643647
648+ @ Test
649+ public void testNormalize31ExclusiveMinMaxStricterThanMinMax () {
650+ OpenAPI openAPI = TestUtils .parseSpec ("src/test/resources/3_1/exclusive-min-max.yaml" );
651+
652+ OpenAPINormalizer n = new OpenAPINormalizer (openAPI , Map .of ("NORMALIZE_31SPEC" , "true" ));
653+ n .normalize ();
654+
655+ Schema <?> schema = openAPI .getPaths ()
656+ .get ("/foo" )
657+ .getGet ()
658+ .getParameters ()
659+ .get (0 )
660+ .getSchema ();
661+
662+ assertEquals (new BigDecimal ("1" ), schema .getExclusiveMinimumValue ());
663+ assertEquals (new BigDecimal ("1" ), schema .getMinimum ());
664+ assertEquals (Boolean .TRUE , schema .getExclusiveMinimum ());
665+
666+ assertEquals (new BigDecimal ("10" ), schema .getExclusiveMaximumValue ());
667+ assertEquals (new BigDecimal ("10" ), schema .getMaximum ());
668+ assertEquals (Boolean .TRUE , schema .getExclusiveMaximum ());
669+ }
670+
671+ @ Test
672+ public void testNormalize31ExclusiveMinMaxEqualToMinMax () {
673+ OpenAPI openAPI = TestUtils .parseSpec ("src/test/resources/3_1/exclusive-min-max.yaml" );
674+
675+ OpenAPINormalizer n = new OpenAPINormalizer (openAPI , Map .of ("NORMALIZE_31SPEC" , "true" ));
676+ n .normalize ();
677+
678+ Schema <?> schema = openAPI .getPaths ()
679+ .get ("/bar" )
680+ .getGet ()
681+ .getParameters ()
682+ .get (0 )
683+ .getSchema ();
684+
685+ // minimum: 0 + exclusiveMinimum: 0 → must remain exclusive
686+ assertEquals (new BigDecimal ("0" ), schema .getExclusiveMinimumValue ());
687+ assertEquals (new BigDecimal ("0" ), schema .getMinimum ());
688+ assertEquals (Boolean .TRUE , schema .getExclusiveMinimum ());
689+
690+ // maximum: 10 + exclusiveMaximum: 10 → must remain exclusive
691+ assertEquals (new BigDecimal ("10" ), schema .getExclusiveMaximumValue ());
692+ assertEquals (new BigDecimal ("10" ), schema .getMaximum ());
693+ assertEquals (Boolean .TRUE , schema .getExclusiveMaximum ());
694+ }
695+
696+ @ Test
697+ public void testNormalize31ExclusiveMinMaxInclusiveStricterThanExclusiveValue () {
698+ OpenAPI openAPI = TestUtils .parseSpec ("src/test/resources/3_1/exclusive-min-max.yaml" );
699+
700+ OpenAPINormalizer n = new OpenAPINormalizer (openAPI , Map .of ("NORMALIZE_31SPEC" , "true" ));
701+ n .normalize ();
702+
703+ Schema <?> schema = openAPI .getPaths ()
704+ .get ("/baz" )
705+ .getGet ()
706+ .getParameters ()
707+ .get (0 )
708+ .getSchema ();
709+
710+ // minimum: 5 is stricter than exclusiveMinimum: 0 (x >= 5 dominates x > 0)
711+ assertEquals (new BigDecimal ("0" ), schema .getExclusiveMinimumValue ());
712+ assertEquals (new BigDecimal ("5" ), schema .getMinimum ());
713+ assertNull (schema .getExclusiveMinimum ());
714+
715+ // maximum: 10 is stricter than exclusiveMaximum: 11 (x <= 10 dominates x < 11)
716+ assertEquals (new BigDecimal ("11" ), schema .getExclusiveMaximumValue ());
717+ assertEquals (new BigDecimal ("10" ), schema .getMaximum ());
718+ assertNull (schema .getExclusiveMaximum ());
719+ }
720+
721+ @ Test
722+ public void testNormalize31ExclusiveMinMaxBooleanExclusiveAlreadySet () {
723+ OpenAPI openAPI = TestUtils .parseSpec ("src/test/resources/3_1/exclusive-min-max.yaml" );
724+
725+ OpenAPINormalizer n = new OpenAPINormalizer (openAPI , Map .of ("NORMALIZE_31SPEC" , "true" ));
726+ n .normalize ();
727+
728+ Schema <?> schema = openAPI .getPaths ()
729+ .get ("/old" )
730+ .getGet ()
731+ .getParameters ()
732+ .get (0 )
733+ .getSchema ();
734+
735+ // 3.0-style boolean exclusive flags should remain intact
736+ assertEquals (new BigDecimal ("0" ), schema .getMinimum ());
737+ assertNull (schema .getExclusiveMinimum ());
738+
739+ assertEquals (new BigDecimal ("10" ), schema .getMaximum ());
740+ assertNull (schema .getExclusiveMaximum ());
741+
742+ // Ensure numeric 3.1 value fields are not unexpectedly set by normalization
743+ assertNull (schema .getExclusiveMinimumValue ());
744+ assertNull (schema .getExclusiveMaximumValue ());
745+ }
746+
644747
645748 @ Test
646749 public void testRemoveXInternal () {
0 commit comments