So I just experienced a type inference issue unique to Scala 3 when dealing with custom function interfaces.
In pekko we had defined our own types of functions, i.e.
/**
* A Function interface. Used to create first-class-functions is Java.
* `Serializable` is needed to be able to grab line number for Java 8 lambdas.
* Supports throwing `Exception` in the apply, which the `java.util.function.Function` counterpart does not.
*/
@nowarn("msg=@SerialVersionUID has no effect")
@SerialVersionUID(1L)
@FunctionalInterface
trait Function[-T, +R] extends java.io.Serializable {
@throws(classOf[Exception])
def apply(param: T): R
}
When trying to call the following function
def mapConcat[T](f: function.Function[Out, _ <: java.lang.Iterable[T]]): javadsl.Source[T, Mat] =
new Source(delegate.mapConcat(elem => Util.immutableSeq(f.apply(elem))))
using lambda syntax that returns a java.util.List
i.e.
streamingPullResult
.mapConcat((response: StreamingPullResponse) => response.getReceivedMessagesList)
You get the following error
[error] -- [E007] Type Mismatch Error: /Users/mdedetrich/github/incubator-pekko-connectors/google-cloud-pub-sub-grpc/src/main/scala/org/apache/pekko/stream/connectors/googlecloud/pubsub/grpc/javadsl/GooglePubSub.scala:75:21
[error] 75 | .mapConcat((response: StreamingPullResponse) => response.getReceivedMessagesList)
[error] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
[error] | Found: com.google.pubsub.v1.StreamingPullResponse =>
[error] | java.util.List[com.google.pubsub.v1.ReceivedMessage]
[error] | Required: org.apache.pekko.japi.function.Function[
[error] | com.google.pubsub.v1.StreamingPullResponse, ? <: Iterable[T]]
[error] |
[error] | where: T is a type variable with constraint
[error] |
[error] | longer explanation available when compiling with `-explain`
Manually specifying the pekko.japi.function.Function
function type, i.e.
streamingPullResult
.mapConcat(
((response: StreamingPullResponse) =>
response.getReceivedMessagesList): pekko.japi.function.Function[StreamingPullResponse,
java.util.List[ReceivedMessage]])
Solves the issue
On Scala 2.12/2.13 this workaround is not necessary. Also see enable scala3 build for more google connectors by pjfanning · Pull Request #165 · apache/incubator-pekko-connectors · GitHub