@@ -700,89 +700,21 @@ function (Expr\ArrayItem $item): Type {
700700}
701701
702702if ($ node instanceof FuncCall && $ node ->name instanceof Name) {
703- $ arrayFunctionsThatDependOnClosureReturnType = [
704- 'array_map ' => 0 ,
705- 'array_reduce ' => 1 ,
706- ];
707- $ functionName = strtolower ((string ) $ node ->name );
708- if (
709- isset ($ arrayFunctionsThatDependOnClosureReturnType [$ functionName ])
710- && isset ($ node ->args [$ arrayFunctionsThatDependOnClosureReturnType [$ functionName ]])
711- && $ node ->args [$ arrayFunctionsThatDependOnClosureReturnType [$ functionName ]]->value instanceof Expr \Closure
712- ) {
713- $ closure = $ node ->args [$ arrayFunctionsThatDependOnClosureReturnType [$ functionName ]]->value ;
714- $ anonymousFunctionType = $ this ->getFunctionType ($ closure ->returnType , $ closure ->returnType === null , false );
715- if ($ functionName === 'array_reduce ' ) {
716- return $ anonymousFunctionType ;
717- }
718-
719- return new ArrayType (
720- $ anonymousFunctionType ,
721- true
722- );
723- }
724-
725- $ arrayFunctionsThatDependOnArgumentType = [
726- 'array_filter ' => 0 ,
727- 'array_unique ' => 0 ,
728- 'array_reverse ' => 0 ,
729- ];
730- if (
731- isset ($ arrayFunctionsThatDependOnArgumentType [$ functionName ])
732- && isset ($ node ->args [$ arrayFunctionsThatDependOnArgumentType [$ functionName ]])
733- ) {
734- $ argumentValue = $ node ->args [$ arrayFunctionsThatDependOnArgumentType [$ functionName ]]->value ;
735- return $ this ->getType ($ argumentValue );
736- }
737-
738- $ arrayFunctionsThatCreateArrayBasedOnArgumentType = [
739- 'array_fill ' => 2 ,
740- 'array_fill_keys ' => 1 ,
741- ];
742- if (
743- isset ($ arrayFunctionsThatCreateArrayBasedOnArgumentType [$ functionName ])
744- && isset ($ node ->args [$ arrayFunctionsThatCreateArrayBasedOnArgumentType [$ functionName ]])
745- ) {
746- $ argumentValue = $ node ->args [$ arrayFunctionsThatCreateArrayBasedOnArgumentType [$ functionName ]]->value ;
747-
748- return new ArrayType ($ this ->getType ($ argumentValue ), true );
703+ if (!$ this ->broker ->hasFunction ($ node ->name , $ this )) {
704+ return new ErrorType ();
749705}
750706
751- $ functionsThatCombineAllArgumentTypes = [
752- 'min ' => '' ,
753- 'max ' => '' ,
754- ];
755- if (
756- isset ($ functionsThatCombineAllArgumentTypes [$ functionName ])
757- && isset ($ node ->args [0 ])
758- ) {
759- if ($ node ->args [0 ]->unpack ) {
760- $ argumentType = $ this ->getType ($ node ->args [0 ]->value );
761- if ($ argumentType instanceof ArrayType) {
762- return $ argumentType ->getItemType ();
763- }
764- }
765-
766- if (count ($ node ->args ) === 1 ) {
767- $ argumentType = $ this ->getType ($ node ->args [0 ]->value );
768- if ($ argumentType instanceof ArrayType) {
769- return $ argumentType ->getItemType ();
770- }
771- }
707+ $ functionReflection = $ this ->broker ->getFunction ($ node ->name , $ this );
772708
773- $ argumentTypes = [];
774- foreach ( $ node -> args as $ arg ) {
775- $ argumentTypes [] = $ this -> getType ( $ arg -> value ) ;
709+ foreach ( $ this -> broker -> getDynamicFunctionReturnTypeExtensions () as $ dynamicFunctionReturnTypeExtension ) {
710+ if (! $ dynamicFunctionReturnTypeExtension -> isFunctionSupported ( $ functionReflection ) ) {
711+ continue ;
776712}
777713
778- return TypeCombinator::union (...$ argumentTypes );
779- }
780-
781- if (!$ this ->broker ->hasFunction ($ node ->name , $ this )) {
782- return new ErrorType ();
714+ return $ dynamicFunctionReturnTypeExtension ->getTypeFromFunctionCall ($ functionReflection , $ node , $ this );
783715}
784716
785- return $ this -> broker -> getFunction ( $ node -> name , $ this ) ->getReturnType ();
717+ return $ functionReflection ->getReturnType ();
786718}
787719
788720return new MixedType ();
@@ -1109,7 +1041,7 @@ private function isParameterValueNullable(Node\Param $parameter): bool
11091041 * @param bool $isVariadic
11101042 * @return Type
11111043 */
1112- private function getFunctionType ($ type = null , bool $ isNullable , bool $ isVariadic ): Type
1044+ public function getFunctionType ($ type = null , bool $ isNullable , bool $ isVariadic ): Type
11131045{
11141046if ($ isNullable ) {
11151047return TypeCombinator::addNull (
0 commit comments