bug icon indicating copy to clipboard operation
bug copied to clipboard

Extension of sealed class on different line should be disallowed in REPL (in lieu of reasonable semantics)

Open pera opened this issue 3 years ago • 7 comments

Reproduction steps

Scala version: 2.13.8 and 2.11.12

~~Example 1~~ [INVALID]

sealed trait MyTrait { def a: Int }
case class MyClass ( a: Int ) extends MyTrait
object MyObject {
  case class MyClass ( a: Int ) extends MyTrait
  ((x: MyTrait) => x match {
    case _: MyClass => x.a
  })(MyClass(123))
}

/* $ scalac test.scala
 * test.scala:5: warning: match may not be exhaustive.
 * It would fail on the following input: MyClass(_)
 *   ((x: MyTrait) => x match {
 *                    ^
 * one warning found
 * /

Example 2:

scala> sealed trait Test { def a: Int }
defined trait Test

scala> case class Test1 ( atypo: Int ) extends Test
<console>:12: error: class Test1 needs to be abstract, since method a in trait Test of type => Int is not defined
       case class Test1 ( atypo: Int ) extends Test
                  ^

scala> case class Test1 ( a: Int ) extends Test
defined class Test1

scala> ((x: Test) => x match {
     |   case xx: Test1 => xx.a
     | })(Test1(123))
<console>:15: warning: match may not be exhaustive.
It would fail on the following input: Test1(_)
       ((x: Test) => x match {
                     ^
res0: Int = 123

Problem

~~In the first example I believe the compiler shouldn't produce any warning.~~ The second example is similar but can only happen in a REPL session. I see there are many open issues with exhaustiveness checking already but I couldn't find anyone similar to this.

pera avatar Sep 13 '22 13:09 pera

In the first example, shadowing is not relevant, though it would be nice if the error message disambiguated when necessary.

(It is not looking at args applied to the function when it reports about the match.)

The second example is the same, but sealed is not treated usefully in REPL across input lines:

Welcome to Scala 2.13.8 (OpenJDK 64-Bit Server VM, Java 18.0.2.1).
Type in expressions for evaluation. Or try :help.

scala> sealed trait MyTrait { def a: Int }
trait MyTrait

scala> final case class MyClass ( a: Int ) extends MyTrait
class MyClass

scala> def f(x: MyTrait): Int = x match { case _: MyClass => x.a }
                                ^
       warning: match may not be exhaustive.
       It would fail on the following input: MyClass(_)
def f(x: MyTrait): Int

scala>
:quit

I don't know offhand why MyClass is allowed, since different lines should be different compilation units. But if it is allowed, then sealedness should work as normal.

scala> sealed trait MyTrait { def a: Int }; final case class MyClass ( a: Int ) extends MyTrait
trait MyTrait
class MyClass

scala> def f(x: MyTrait): Int = x match { case _: MyClass => x.a }
def f(x: MyTrait): Int

scala>

som-snytt avatar Sep 13 '22 16:09 som-snytt

Thanks @som-snytt that makes sense and sorry for the misreport in the first example, I am new to Scala and the error message was a bit confusing so I assumed something regarding scoping rules that was wrong. It would be nice indeed if the message could disambiguate between the two by including the fqn maybe? I have edited the original report to make clear that this issue is just for the REPL example.

pera avatar Sep 14 '22 07:09 pera

We don't keep "error message X could be improved" tickets open, but regardless, pull requests with such improvments are always welcome.

I am new to Scala

Please use https://users.scala-lang.org for questions. See also https://scala-lang.org/community for ideas on other places you can ask questions about Scala.

SethTisue avatar Sep 17 '22 01:09 SethTisue

Scala 3 REPL says extension is not allowed; like I said, it's different compilation units. (Dotty uses the quaint phrase, "source file".)

Welcome to Scala 3.2.0 (18.0.2.1, Java OpenJDK 64-Bit Server VM).
Type in expressions for evaluation. Or try :help.

scala> sealed trait MyTrait { def a: Int }
// defined trait MyTrait

scala> final case class MyClass ( a: Int ) extends MyTrait
-- [E112] Syntax Error: ------------------------------------------------------------------------------------------------
1 |final case class MyClass ( a: Int ) extends MyTrait
  |                 ^
  |                 Cannot extend sealed trait MyTrait in a different source file
  |
  | longer explanation available when compiling with `-explain`
1 error found

som-snytt avatar Sep 17 '22 03:09 som-snytt

oops... thanks for correcting/clarifying

SethTisue avatar Sep 17 '22 05:09 SethTisue

I don't mind changing the title again if necessary.

som-snytt avatar Sep 17 '22 05:09 som-snytt

“Behind our efforts, let there be found our efforts.”

SethTisue avatar Sep 17 '22 14:09 SethTisue