luau icon indicating copy to clipboard operation
luau copied to clipboard

Solver fails in case of multiple numeric operations

Open OverHash opened this issue 1 year ago • 2 comments

The following Luau code causes blocked types to appear:

--!strict

local module = {}

type TweenInfo = {
    new: (time: number?) -> TweenInfo
}

local TweenInfo: TweenInfo = (nil :: any) :: TweenInfo

function addMoney(amount)
	local info = TweenInfo.new(0.1 * amount + 1.2)
end

return module

Specifically, the 0.1 * amount + 1.2 call will cause a TypeError: Operator '*' could not be applied to operands of types number and unknown; there is no corresponding overload for __mul error.

However, the type of info then becomes local info: *blocked-1221*, which is not fine.

To be honest, I'm not sure what the correct behavior is here. I would guess that the solver should still resolver amount to be have both mul and add operations defined somehow.

OverHash avatar Sep 20 '24 07:09 OverHash

The problem here is that we can't pin down an exact type for amount. In principle, the solution here would be constrained generics so that we could say something like amount : T where mul<number, T> + add<mul<number, T>>.

Secondarily, we should also be reporting a much more sensible error in this case.

For now, you should be able to work around this issue by adding a type annotation:

function addMoney(amount: number) ... end

andyfriesen avatar Jan 21 '25 21:01 andyfriesen

A bit of a quibble: we ought to be able to infer that addMoney has type <T>(amount: T) -> (), but internally we'll error as we'll end up with incompatible types number and add<mul<number, T>, number>. We also shouldn't end up with that blocked type.

hgoldstein avatar Jan 28 '25 18:01 hgoldstein