scala / scala3

The Scala 3 compiler, also known as Dotty.
https://dotty.epfl.ch
Apache License 2.0
5.86k stars 1.06k forks source link

local variable name in function parameter shadows package name #11044

Closed scalavision closed 3 years ago

scalavision commented 3 years ago

Minimized code

package interrupt

sealed trait InterruptType
case class Stop() extends InterruptType

final class Interrupt {

  def stop(interrupt: String) =
    println(interrupt)
    interrupt.Stop()
}

Output

[error] -- [E008] Not Found Error: /home/yoda/Projects/tmp/scala3-example-project/src/main/scala/minimal/SmallTest.scala:10:14 
[error] 10 |    interrupt.Stop()
[error]    |    ^^^^^^^^^^^^^^
[error]    |    value Stop is not a member of String - did you mean interrupt.strip?

Expectation

should compile (it is compiling in scala 2.13)

som-snytt commented 3 years ago

If you supply the braces required for "old-school" lexical scoping, scala 2 demonstrates the same correct shadowing.

➜  snips cat i11044.scala
package interrupt

sealed trait InterruptType
case class Stop() extends InterruptType

final class Interrupt {

  def stop(interrupt: String) = {
    println(interrupt)
    interrupt.Stop()
  }
}
➜  snips scalac i11044.scala
i11044.scala:10: error: value Stop is not a member of String
    interrupt.Stop()
              ^
1 error
➜  snips scalac -version
Scala compiler version 2.13.4 -- Copyright 2002-2020, LAMP/EPFL and Lightbend, Inc.
➜  snips

I thought shadowing an inherited definition was an error now? but I get the same error message.

trait T {
  def interrupt = 42
}

final class Interrupt extends T {

  def stop(interrupt: String) = {
    interrupt.Stop()
  }
}

I must be missing something. I was going to test whether bindings introduced by package clauses also conflict with local defs.

Edit: it was inherited shadowing local def, where new T {} doesn't make it obvious that interrupt is in play.

scalavision commented 3 years ago

yeah.. I forgot adding the curly braces in my example, sorry. I encountered this when trying to update zio lib to support scala3-M3, here:

https://github.com/zio/zio/pull/4516/files#diff-55db93d1616fb3c94a9699b1194a5778e50bc20c9390fe5ed3a5671cafa330c1

This works at least with scala 2.13, and probably also with M2, so it might be a regression somewhere. Thanks for looking into this.

griggt commented 3 years ago

The Scala Language Specification, section 9.4 says:

If a package name is shadowed, it's possible to refer to its fully-qualified name by prefixing it with the special predefined name _root_, which refers to the outermost root package that contains all top-level packages.

which is how we handled that particular update to ZIO for 3.0.0-M3 in the dotty community build: https://github.com/dotty-staging/zio/commit/c08d2b0bd87de82617ae71fc3922292bc8f7b194 (the change itself is needed due to the new creator applications scheme in #10784)

The _root_ construct was already used elsewhere in ZIO, e.g.: https://github.com/zio/zio/blob/4501f16ac57385ec54a38164b145a55c25726379/core/shared/src/main/scala/zio/ZIO.scala#L4326

scalavision commented 3 years ago

thank you @griggt, I guess this one can be closed then, or did you discover anything else @som-snytt ? Sorry for the inconvenience!

b-studios commented 3 years ago

Thanks @griggt, I am closing this issue for the time being.