Skip to content

Non-trivial implicit resolution fails when using default implicit parameters #23555

@bdmendes

Description

@bdmendes

Compiler version

3.7.1

Minimized code

//> using scala "3.7.1"
//> using platform "jvm"

trait Behavior[A] {}

object Behavior {
  implicit def mapBehavior[A: Behavior]: Behavior[List[A]] = new Behavior[List[A]] {}
}

object Model {
  case class Foo(i: Int)
  object Foo {
    given Behavior[Foo] = new Behavior[Foo] {}
    implicit def dummy[A: Behavior](implicit s: String = "hello"): Option[A] = None
  }
}

object App {
    def main(args: Array[String]) = {
      import Model.Foo
      val c = implicitly[Option[List[Foo]]]
    }
}

Output

Compiling project (Scala 3.7.1, JVM (21))
[error] ./bug.scala:20:40
[error] No given instance of type Option[List[Model.Foo]] was found for parameter e of method implicitly in object Predef.
[error] I found:
[error] 
[error]     Model.Foo.dummy[List[Model.Foo]](
[error]       evidence$1 = Behavior.mapBehavior[A](Model.Foo.given_Behavior_Foo))
[error] 
[error] But method dummy in object Foo does not match type Option[List[Model.Foo]].
[error]   val c = implicitly[Option[List[Foo]]]
[error]                                        ^
Error compiling project (Scala 3.7.1, JVM (21))
Compilation failed

Expectation

The implicit "hello" value for String should allow to synthesize a value of type Option[List[Foo]]. Note that this example passes if the file extension is .sc and fails if the file extension is .scala (and in any real project setting).

The example will compile in any setting if I:

  • Provide a String in the trait scope, or
  • Require the implicits in separate parameter lists as in: given [A: Behavior](using s: String = "hello")(using Behavior[A]), which is very weird.

This is noticeable e.g. when depending on pekko-http-circe for completing Pekko HTTP routes.

(In a sidenote, I found zero references to this Scala feature (default implicit parameters), specifically in Scala 3 resources, and I am not a fan of it. Anyway, I'm expecting this to be still perfectly valid Scala code.)

Metadata

Metadata

Assignees

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions