Skip to content

Commit eeda658

Browse files
Merge pull request #8962 from dotty-staging/fix-#8520-2
Fix #8520: Add Reflection.Symbol.typeMembers
2 parents 4ebbdd0 + 5a4fe89 commit eeda658

File tree

6 files changed

+45
-0
lines changed

6 files changed

+45
-0
lines changed

compiler/src/dotty/tools/dotc/tastyreflect/ReflectionCompilerInterface.scala

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1738,6 +1738,12 @@ class ReflectionCompilerInterface(val rootContext: core.Contexts.Context) extend
17381738
case sym if isMethod(sym) && sym.name.toString == name => sym.asTerm
17391739
}.toList
17401740

1741+
def Symbol_typeMembers(self: Symbol)(using ctx: Context): List[Symbol] =
1742+
self.unforcedDecls.filter(_.isType)
1743+
1744+
def Symbol_typeMember(self: Symbol)(name: String)(using ctx: Context): Symbol =
1745+
self.unforcedDecls.find(sym => sym.name == name.toTypeName)
1746+
17411747
def Symbol_classMethods(self: Symbol)(using ctx: Context): List[Symbol] =
17421748
self.typeRef.decls.iterator.collect {
17431749
case sym if isMethod(sym) => sym.asTerm

library/src/scala/tasty/Reflection.scala

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2225,6 +2225,14 @@ class Reflection(private[scala] val internal: CompilerInterface) { self =>
22252225
def classMethods(using ctx: Context): List[Symbol] =
22262226
internal.Symbol_classMethods(sym)
22272227

2228+
/** Type member directly declared in the class */
2229+
def typeMembers(using ctx: Context): List[Symbol] =
2230+
internal.Symbol_typeMembers(sym)
2231+
2232+
/** Type member with the given name directly declared in the class */
2233+
def typeMember(name: String)(using ctx: Context): Symbol =
2234+
internal.Symbol_typeMember(sym)(name)
2235+
22282236
/** Get named non-private methods declared or inherited */
22292237
def method(name: String)(using ctx: Context): List[Symbol] =
22302238
internal.Symbol_method(sym)(name)

library/src/scala/tasty/reflect/CompilerInterface.scala

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1313,6 +1313,12 @@ trait CompilerInterface {
13131313
/** Get all non-private methods declared or inherited */
13141314
def Symbol_methods(self: Symbol)(using ctx: Context): List[Symbol]
13151315

1316+
/** Type member directly declared in the class */
1317+
def Symbol_typeMembers(self: Symbol)(using ctx: Context): List[Symbol]
1318+
1319+
/** Type member with the given name directly declared in the class */
1320+
def Symbol_typeMember(self: Symbol)(name: String)(using ctx: Context): Symbol
1321+
13161322
/** The symbols of each type parameter list and value parameter list of this
13171323
* method, or Nil if this isn't a method.
13181324
*/

tests/run-macros/i8520.check

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
List((A,+))
2+
List((B,-))
3+
List((C, ))

tests/run-macros/i8520/Macro_1.scala

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import scala.quoted._
2+
3+
inline def test[T[_]]: Unit = ${ testExpr[T] }
4+
5+
def testExpr[T[_]: Type](using QuoteContext): Expr[Unit] = {
6+
import qctx.tasty._
7+
def variance(f: Flags) =
8+
if f.is(Flags.Covariant) then "+"
9+
else if f.is(Flags.Contravariant) then "-"
10+
else " "
11+
val t = '[T].unseal.tpe.typeSymbol.typeMembers.map(x => (x.name, variance(x.flags)))
12+
'{ println(${Expr(t.toString)}) }
13+
}

tests/run-macros/i8520/Test_2.scala

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
trait X[+A]
2+
trait Y[-B]
3+
trait Z[C]
4+
5+
@main def Test = {
6+
test[X]
7+
test[Y]
8+
test[Z]
9+
}

0 commit comments

Comments
 (0)