3030use function array_key_exists ;
3131use function count ;
3232use function implode ;
33+ use function in_array ;
3334use function is_int ;
3435use function is_string ;
3536use function max ;
@@ -128,30 +129,32 @@ public function check(
128129 if ($ arg ->unpack ) {
129130 $ arrays = $ type ->getConstantArrays ();
130131 if (count ($ arrays ) > 0 ) {
131- $ minKeys = null ;
132+ $ maxKeys = null ;
132133 foreach ($ arrays as $ array ) {
133134 $ countType = $ array ->getArraySize ();
134135 if ($ countType instanceof ConstantIntegerType) {
135136 $ keysCount = $ countType ->getValue ();
136137 } elseif ($ countType instanceof IntegerRangeType) {
137- $ keysCount = $ countType ->getMin ();
138+ $ keysCount = $ countType ->getMax ();
138139 if ($ keysCount === null ) {
139140 throw new ShouldNotHappenException ();
140141 }
141142 } else {
142143 throw new ShouldNotHappenException ();
143144 }
144- if ($ minKeys !== null && $ keysCount >= $ minKeys ) {
145+ if ($ maxKeys !== null && $ keysCount >= $ maxKeys ) {
145146 continue ;
146147 }
147148
148- $ minKeys = $ keysCount ;
149+ $ maxKeys = $ keysCount ;
149150 }
150151
151- for ($ j = 0 ; $ j < $ minKeys ; $ j ++) {
152+ for ($ j = 0 ; $ j < $ maxKeys ; $ j ++) {
152153 $ types = [];
153154 $ commonKey = null ;
155+ $ isOptionalKey = false ;
154156 foreach ($ arrays as $ constantArray ) {
157+ $ isOptionalKey = in_array ($ j , $ constantArray ->getOptionalKeys (), true );
155158 $ types [] = $ constantArray ->getValueTypes ()[$ j ];
156159 $ keyType = $ constantArray ->getKeyTypes ()[$ j ];
157160 if ($ commonKey === null ) {
@@ -165,6 +168,10 @@ public function check(
165168 $ keyArgumentName = $ commonKey ;
166169 $ hasNamedArguments = true ;
167170 }
171+ if ($ isOptionalKey ) {
172+ continue ;
173+ }
174+
168175 $ arguments [] = [
169176 $ arg ->value ,
170177 TypeCombinator::union (...$ types ),
0 commit comments