diff --git a/compiler/src/dotty/tools/dotc/reporting/diagnostic/ErrorMessageID.java b/compiler/src/dotty/tools/dotc/reporting/diagnostic/ErrorMessageID.java index 99311fd1cfc1..2e2182abd131 100644 --- a/compiler/src/dotty/tools/dotc/reporting/diagnostic/ErrorMessageID.java +++ b/compiler/src/dotty/tools/dotc/reporting/diagnostic/ErrorMessageID.java @@ -134,7 +134,8 @@ public enum ErrorMessageID { TermMemberNeedsNeedsResultTypeForImplicitSearchID, CaseClassCannotExtendEnumID, ValueClassParameterMayNotBeCallByNameID, - NotAnExtractorID + NotAnExtractorID, + MemberWithSameNameAsStaticID ; public int errorNumber() { diff --git a/compiler/src/dotty/tools/dotc/reporting/diagnostic/messages.scala b/compiler/src/dotty/tools/dotc/reporting/diagnostic/messages.scala index 10ac5e7356ea..64979acf1721 100644 --- a/compiler/src/dotty/tools/dotc/reporting/diagnostic/messages.scala +++ b/compiler/src/dotty/tools/dotc/reporting/diagnostic/messages.scala @@ -2131,4 +2131,12 @@ object messages { |For this reason, you can also define patterns through `unapplySeq` which returns `Option[Seq[T]]`. |This mechanism is used for instance in pattern `case List(x1, ..., xn)`""".stripMargin } + + case class MemberWithSameNameAsStatic()(implicit val ctx: Context) + extends Message(MemberWithSameNameAsStaticID) { + + override def msg: String = hl"Companion classes cannot define members with same name as a @static member" + override def kind: String = "Syntax" + override def explanation: String = "" + } } diff --git a/compiler/src/dotty/tools/dotc/transform/CheckStatic.scala b/compiler/src/dotty/tools/dotc/transform/CheckStatic.scala index cb27f2d7323b..70f448e380d3 100644 --- a/compiler/src/dotty/tools/dotc/transform/CheckStatic.scala +++ b/compiler/src/dotty/tools/dotc/transform/CheckStatic.scala @@ -8,7 +8,7 @@ import Contexts.Context import Symbols._ import dotty.tools.dotc.ast.tpd import Decorators._ -import reporting.diagnostic.messages.{MissingCompanionForStatic, StaticFieldsOnlyAllowedInObjects} +import reporting.diagnostic.messages.{MemberWithSameNameAsStatic, MissingCompanionForStatic, StaticFieldsOnlyAllowedInObjects} /** A transformer that check that requirements of Static fields\methods are implemented: * 1. Only objects can have members annotated with `@static` @@ -46,7 +46,7 @@ class CheckStatic extends MiniPhase { if (!companion.exists) { ctx.error(MissingCompanionForStatic(defn.symbol), defn.pos) } else if (clashes.exists) { - ctx.error("companion classes cannot define members with same name as @static member", defn.pos) + ctx.error(MemberWithSameNameAsStatic(), defn.pos) } else if (defn.symbol.is(Flags.Mutable) && companion.is(Flags.Trait)) { ctx.error("Companions of traits cannot define mutable @static fields", defn.pos) } else if (defn.symbol.is(Flags.Lazy)) { diff --git a/compiler/test/dotty/tools/dotc/reporting/ErrorMessagesTests.scala b/compiler/test/dotty/tools/dotc/reporting/ErrorMessagesTests.scala index 78b52cdb1a11..b8018ba39b4c 100644 --- a/compiler/test/dotty/tools/dotc/reporting/ErrorMessagesTests.scala +++ b/compiler/test/dotty/tools/dotc/reporting/ErrorMessagesTests.scala @@ -1527,4 +1527,22 @@ class ErrorMessagesTests extends ErrorMessagesTest { val NotAnExtractor(tree) = messages.head assertEquals("Foo", tree.show) } + + @Test def memberWithSameNameAsStatic() = + checkMessagesAfter(CheckStatic.name) { + """ + |import scala.annotation.static + |class Camp { + | val name = "" + |} + |object Camp { + | @static val name = "" + |} + """.stripMargin + }.expect { (_, messages) => + assertMessageCount(1, messages) + val message = messages.head + assertTrue(message.isInstanceOf[MemberWithSameNameAsStatic]) + assertEquals(message.msg, "Companion classes cannot define members with same name as a @static member") + } }