When you have an array of BlockNodes, it would be understandable if you wanted to filter said array to get a list of a specific node, KinjaVideo for example. Flow doesn’t support that, unfortunately.
Here you would assume that videoNodes is an Array<KinjaVideoJSON>. However, if you check the type signature of Array.filter, it turns out that it’s just Array<T> => Array<T>, so there’s no type narrowing taking place, the resulting array will be the same type as the original.
The reasoning behind this is that flow doesn’t know what happens inside isKinjaVideo (neither should it), it only knows that it returns a boolean, it doesn’t know that that boolean signifies that the input blockNode is actually a KinjaVideo. This would be called a predicate, and typescript does support it. It actually seems like flow would support something similar as well, but I couldn’t get it to work, probably because of the type signature of Array.filter.
This is not something you can fix. The only solution is to use Array.reduce instead, which is nicely typed as Array<T> => U:
Note that in some form we need to provide a type definition in the above example. Either by specifying the type of videoNodes, or by passing in a type parameter for Array.reduce (I prefer the latter).