Skip to content
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

Add error reporting for mirror synthesis #15164

Merged
merged 5 commits into from May 13, 2022
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
4 changes: 2 additions & 2 deletions compiler/src/dotty/tools/dotc/typer/Synthesizer.scala
Expand Up @@ -327,7 +327,7 @@ class Synthesizer(typer: Typer)(using @constructorOnly c: Context):
val reason = if !cls.isGenericProduct then
i"because ${cls.whyNotGenericProduct}"
else if !canAccessCtor(cls) then
i"because constructor of $cls is unnaccessible from the calling scope."
i"because the constructor of $cls is innaccessible from the calling scope."
else
""
i"$cls is not a generic product $reason"
Expand Down Expand Up @@ -618,7 +618,7 @@ object Synthesizer:
private def orElse(treeWithErrors1: TreeWithErrors, treeWithErrors2: => TreeWithErrors): TreeWithErrors = treeWithErrors1 match
case (tree, errors) if tree eq genericEmptyTree =>
val (tree2, errors2) = treeWithErrors2
(tree2, errors2 ::: errors)
(tree2, errors ::: errors2)
case _ => treeWithErrors1

private def clearErrorsIfNotEmpty(treeWithErrors: TreeWithErrors) = treeWithErrors match
Expand Down
2 changes: 1 addition & 1 deletion tests/neg/i14432.check
Expand Up @@ -2,5 +2,5 @@
13 |val mFoo = summon[Mirror.Of[Foo]] // error: no mirror found
| ^
|No given instance of type deriving.Mirror.Of[example.Foo] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[example.Foo]:
| * class Foo is not a generic product because the constructor of class Foo is innaccessible from the calling scope.
| * class Foo is not a generic sum because it is not a sealed class
| * class Foo is not a generic product because constructor of class Foo is unnaccessible from the calling scope.
2 changes: 1 addition & 1 deletion tests/neg/i14432a.check
Expand Up @@ -2,5 +2,5 @@
14 | val mFoo = summon[Mirror.Of[example.Foo]] // error: no mirror found
| ^
|No given instance of type deriving.Mirror.Of[example.Foo] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[example.Foo]:
| * class Foo is not a generic product because the constructor of class Foo is innaccessible from the calling scope.
| * class Foo is not a generic sum because it is not a sealed class
| * class Foo is not a generic product because constructor of class Foo is unnaccessible from the calling scope.
2 changes: 1 addition & 1 deletion tests/neg/i14432b.check
Expand Up @@ -2,5 +2,5 @@
15 | val mFoo = summon[Mirror.Of[example.Foo]] // error: no mirror found
| ^
|No given instance of type deriving.Mirror.Of[example.Foo] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[example.Foo]:
| * class Foo is not a generic product because the constructor of class Foo is innaccessible from the calling scope.
| * class Foo is not a generic sum because it is not a sealed class
| * class Foo is not a generic product because constructor of class Foo is unnaccessible from the calling scope.
2 changes: 1 addition & 1 deletion tests/neg/i14432c.check
Expand Up @@ -10,5 +10,5 @@
16 | val mFoo = summon[Mirror.Of[example.Foo]] // error: no mirror
| ^
|No given instance of type deriving.Mirror.Of[example.Foo] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[example.Foo]:
| * class Foo is not a generic product because the constructor of class Foo is innaccessible from the calling scope.
| * class Foo is not a generic sum because it is not a sealed class
| * class Foo is not a generic product because constructor of class Foo is unnaccessible from the calling scope.
2 changes: 1 addition & 1 deletion tests/neg/i14432d.check
Expand Up @@ -2,5 +2,5 @@
17 | val mFoo = summon[Mirror.Of[example.Foo]] // error
| ^
|No given instance of type deriving.Mirror.Of[example.Foo] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[example.Foo]:
| * class Foo is not a generic product because the constructor of class Foo is innaccessible from the calling scope.
| * class Foo is not a generic sum because it is not a sealed class
| * class Foo is not a generic product because constructor of class Foo is unnaccessible from the calling scope.
2 changes: 1 addition & 1 deletion tests/neg/i14823.check
Expand Up @@ -2,5 +2,5 @@
8 |val baz = summon[Mirror.Of[SubA[Int] | SubB[Int]]] // error
| ^
|No given instance of type deriving.Mirror.Of[SubA[Int] | SubB[Int]] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[SubA[Int] | SubB[Int]]:
| * class Cov is not a generic sum because it is not a sealed class
| * class Cov is not a generic product
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is another interesting one, to the user seeing this error, it might not be obvious why the error mentions Cov, and not SubA or SubB, I think this can wait for a new PR but perhaps we should explain why the union collapses to its common superclass, which is why we reject it.

| * class Cov is not a generic sum because it is not a sealed class
14 changes: 7 additions & 7 deletions tests/neg/mirror-synthesis-errors.check
Expand Up @@ -2,41 +2,41 @@
21 |val testA = summon[Mirror.Of[A]] // error: Not a sealed trait
| ^
|No given instance of type deriving.Mirror.Of[A] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[A]:
| * trait A is not a generic sum because it is not a sealed trait
| * trait A is not a generic product because it is not a case class
| * trait A is not a generic sum because it is not a sealed trait
-- Error: tests/neg/mirror-synthesis-errors.scala:22:32 ----------------------------------------------------------------
22 |val testC = summon[Mirror.Of[C]] // error: Does not have subclasses
| ^
|No given instance of type deriving.Mirror.Of[C] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[C]:
| * trait C is not a generic sum because it does not have subclasses
| * trait C is not a generic product because it is not a case class
| * trait C is not a generic sum because it does not have subclasses
-- Error: tests/neg/mirror-synthesis-errors.scala:23:32 ----------------------------------------------------------------
23 |val testD = summon[Mirror.Of[D]] // error: child SubD takes more than one parameter list
| ^
|No given instance of type deriving.Mirror.Of[D] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[D]:
| * class D is not a generic sum because its child class SubD is not a generic product because it takes more than one parameter list
| * class D is not a generic product because it is not a case class
| * class D is not a generic sum because its child class SubD is not a generic product because it takes more than one parameter list
-- Error: tests/neg/mirror-synthesis-errors.scala:24:38 ----------------------------------------------------------------
24 |val testSubD = summon[Mirror.Of[SubD]] // error: takes more than one parameter list
| ^
|No given instance of type deriving.Mirror.Of[SubD] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[SubD]:
| * class SubD is not a generic sum because it is not a sealed class
| * class SubD is not a generic product because it takes more than one parameter list
| * class SubD is not a generic sum because it is not a sealed class
-- Error: tests/neg/mirror-synthesis-errors.scala:25:32 ----------------------------------------------------------------
25 |val testE = summon[Mirror.Of[E]] // error: Not an abstract class
| ^
|No given instance of type deriving.Mirror.Of[E] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[E]:
| * class E is not a generic sum because it is not an abstract class
| * class E is not a generic product because it is not a case class
| * class E is not a generic sum because it is not an abstract class
-- Error: tests/neg/mirror-synthesis-errors.scala:26:32 ----------------------------------------------------------------
26 |val testF = summon[Mirror.Of[F]] // error: No children
| ^
|No given instance of type deriving.Mirror.Of[F] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[F]:
| * trait F is not a generic sum because it does not have subclasses
| * trait F is not a generic product because it is not a case class
| * trait F is not a generic sum because it does not have subclasses
-- Error: tests/neg/mirror-synthesis-errors.scala:27:36 ----------------------------------------------------------------
27 |val testG = summon[Mirror.Of[Foo.G]] // error: Has anonymous subclasses
| ^
|No given instance of type deriving.Mirror.Of[Foo.G] was found for parameter x of method summon in object Predef. Failed to synthesize an instance of type deriving.Mirror.Of[Foo.G]:
| * trait G is not a generic sum because it has anonymous or inaccessible subclasses
| * trait G is not a generic product because it is not a case class
| * trait G is not a generic sum because it has anonymous or inaccessible subclasses