-
Notifications
You must be signed in to change notification settings - Fork 1.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Cannot summon Type[T] from Quotes #21696
Comments
Hi @tribbloid, This is actually the correct behavior. Since Scala is subject to the erasure of type parameters, we don't have enough information at runtime to be able to execute To fix the provided snippet, here is the change to do: import scala.quoted.{Expr, Quotes, Type}
case class Thing[T](vs: List[String])
def deserialize[T: Type](expr: Expr[List[String]])(using Quotes): Expr[Thing[T]] = {
'{ Thing[T]($expr) }
} |
I'm keeping the ticket open to see if we might benefit from a better error reporting |
@hamzaremmal I doubt if it could be that simple, everything defined in the example is indeed compile-time only. But you are right it is not revealing enough, may I suggest a better example? comparing the following 2 cases: (error) object Demo1 {
object TASTyLowering {
def deserialize[T](expr: Expr[List[String]])(
using
qt: Quotes,
tt: Type[T]
): Expr[Thing[T]] = {
'{ Thing[T]($expr) }
}
}
def deserialize[T](expr: Expr[List[String]])(
using
Quotes
): Expr[Thing[T]] = {
TASTyLowering.deserialize(expr)
}
} (success) object Demo2 {
object TASTyLowering {
def deserialize[T](expr: Expr[List[String]])(
using
qt: Quotes,
tt: Type[T]
): Expr[T] = {
'{ ($expr).asInstanceOf[T] }
}
}
def deserialize[T](expr: Expr[List[String]])(
using
Quotes
): Expr[T] = {
TASTyLowering.deserialize(expr)
}
} The successful case only differs in return type of the |
About these two snippets, the first one is expecting to fail as I explained in my previous message, we should provide the witness ( [[syntax trees at end of typer]] // /Users/hamzaremmal/Desktop/LAMP/playground/i21696/src/demo2.scala
package <empty> {
import scala.quoted.*
final lazy module val Demo2: Demo2 = new Demo2()
final module class Demo2() extends Object() { this: Demo2.type =>
final lazy module val TASTyLowering: Demo2.TASTyLowering =
new Demo2.TASTyLowering()
final module class TASTyLowering() extends Object() {
this: Demo2.TASTyLowering.type =>
def deserialize[T >: Nothing <: Any](expr: scala.quoted.Expr[List[String]]
)(implicit evidence$1: scala.quoted.Type[T], x$2: scala.quoted.Quotes):
scala.quoted.Expr[T] =
'{
${
{
def $anonfun(using contextual$1: scala.quoted.Quotes):
scala.quoted.Expr[List[String]] = expr
closure($anonfun)
}
}.asInstanceOf[T]
}.apply(x$2)
}
def deserialize[T >: Nothing <: Any](expr: scala.quoted.Expr[List[String]])(
using x$2: scala.quoted.Quotes): scala.quoted.Expr[T] =
Demo2.TASTyLowering.deserialize[Nothing](expr)(
scala.quoted.Type.of[Nothing](x$2), x$2)
}
} Since the type is instanciated to EDIT: It will be hard to avoid collapsing to |
wow I never realise that,, Thanks a lot for pointing that out! theoretically, this could also happen if Thing[?] is covariant (collapse to Nothing) or contravariant (collapse to Any). Let me try it shortly ... |
😄
Yes, it can happen and in the provided example, it will happen. |
Compiler version
3.5.1
Minimized code
Output
the signature of
Type.of[T]
is:so clearly something is wrong here
Expectation
both summoning should succeed
The text was updated successfully, but these errors were encountered: