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

REPL shadowing broken under :paste -raw #12034

Open
som-snytt opened this issue Jun 10, 2020 · 3 comments
Open

REPL shadowing broken under :paste -raw #12034

som-snytt opened this issue Jun 10, 2020 · 3 comments
Labels
Milestone

Comments

@som-snytt
Copy link

reproduction steps

using Scala 2.13.2,

scala> new C
val res0: C = extantC

scala> class C { override def toString = "lineC" }
class C

scala> new C
val res1: C = lineC

scala> :pa -raw
// Entering paste mode (ctrl-D to finish)

class C { override def toString = "rawC" }


// Exiting paste mode, now interpreting.


scala> new C
val res2: C = lineC

scala> :pa -raw
// Entering paste mode (ctrl-D to finish)

package c { class C { override def toString = "rawC" } }


// Exiting paste mode, now interpreting.


scala> new c.C
val res4: c.C = rawC

scala> :pa -raw
// Entering paste mode (ctrl-D to finish)

package c { class C { override def toString = "rawC2" } }


// Exiting paste mode, now interpreting.


scala> new c.C
val res5: c.C = rawC

scala> :reset
Resetting interpreter state.
Forgetting this session history:

new C
class C { override def toString = "lineC" }
new C
new C
new c.C
new c.C

Forgetting all expression results and named terms: $intp
Forgetting defined types: C

scala> new c.C
java.lang.NoClassDefFoundError: c/C
  at java.lang.Class.getDeclaredMethods0(Native Method)
  at java.lang.Class.privateGetDeclaredMethods(Class.java:2701)
  at java.lang.Class.privateGetPublicMethods(Class.java:2902)
  at java.lang.Class.getMethods(Class.java:1615)
  at scala.tools.nsc.interpreter.IMain$ReadEvalPrint.evalMethod(IMain.scala:728)
[snip]
Caused by: java.lang.ClassNotFoundException: c.C
  at scala.reflect.internal.util.AbstractFileClassLoader.findClass(AbstractFileClassLoader.scala:71)
  at java.lang.ClassLoader.loadClass(ClassLoader.java:418)
  at java.lang.ClassLoader.loadClass(ClassLoader.java:351)
  ... 27 more

scala> :pa -raw
// Entering paste mode (ctrl-D to finish)

package c { class C { override def toString = "rawC2" } }


// Exiting paste mode, now interpreting.


scala> new c.C
val res1: c.C = rawC2

Also,

scala> :pa -raw
// Entering paste mode (ctrl-D to finish)

class C { override def toString = "rawC" }


// Exiting paste mode, now interpreting.


scala> new C
val res1: C = extantC

problem

Apparent shadowing is confusing.

An existing class on the class path is "shadowed" by a class in a line package, because REPL scope is consulted first for import candidates. That makes sense, though it might be nice to warn when a logical class name changes provenance.

A rawly pasted class is hidden by an existing class on the class path. That is probably only an issue for default empty package, so maybe keeping it off the class path would be a feature.

You can't redefine a class with raw paste.

:reset has a hiccup as shown.

Maybe what's needed is class loader management to go along with history management (collecting previously computed values).

@som-snytt som-snytt added the repl label Jun 10, 2020
@Jasper-M
Copy link
Member

Here's another one.

scala> :pa -raw
// Entering paste mode (ctrl-D to finish)

class C


// Exiting paste mode, now interpreting.


scala> new C
val res0: C = C@5cd25b58

scala> :pa -raw
// Entering paste mode (ctrl-D to finish)

class C { def foo = 0 }


// Exiting paste mode, now interpreting.


scala> new C().foo
java.lang.NoSuchMethodError: C.foo()I
  ... 40 elided

@dwijnand dwijnand changed the title REPL shadowing is confusing REPL shadowing broken under :paste -raw Nov 18, 2020
@SethTisue
Copy link
Member

SethTisue commented Nov 18, 2020

fwiw I think of :paste -raw as power-user, hackers-only, you're-on-your-own-here stuff. When I use it, I use it exactly once, at the beginning of a REPL session, and then if I need to change something, I restart the REPL.

@dwijnand
Copy link
Member

Without :paste and with standard :paste things seem to define as expected, so I amended the title:

scala> class C { override def toString = "lineC" }
class C

scala> new C
val res0: C = lineC

scala> class C { override def toString = "rawC" }
class C

scala> new C
val res1: C = rawC
scala> class C { override def toString = "lineC" }
class C

scala> new C
val res0: C = lineC

scala> :paste
// Entering paste mode (ctrl-D to finish)

class C { override def toString = "pasteC" }


// Exiting paste mode, now interpreting.

class C

scala> new C
val res1: C = pasteC

@dwijnand dwijnand added this to the Backlog milestone Nov 18, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

4 participants