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

Cannot go to dependecy for summonFrom #4366

Open
kpodsiad opened this issue Sep 9, 2022 · 2 comments
Open

Cannot go to dependecy for summonFrom #4366

kpodsiad opened this issue Sep 9, 2022 · 2 comments
Labels
navigation Related to goto definition, find references, open symbol presentation-compiler Something relating to the presentation compiler Scala 3 Generic ticket relating to Scala 3 upstream-fix-needed Waiting on a fix upstream

Comments

@kpodsiad
Copy link
Member

kpodsiad commented Sep 9, 2022

Describe the bug

Execute Go to definition on

//> using scala "3.2.0"

import scala.compiletime.*

trait Typeclass[+A]

object Main extends App:
  inline def foo = {
    summon@@From {
      case given Typeclass[Int] => 0
      case _                    => 1
    }
  }

it doesn't work. However, summon@@From() works but argument of summonFrom must be pattern matching closure so one has to always use {} brackets.

Expected behavior

Go to definition works

Operating system

macOS

Editor/Extension

VS Code

Version of Metals

v0.11.8

Extra context or search terms

scala 3, go to definiton, summonFrom

@kpodsiad
Copy link
Member Author

MetalsInteractive.enclosingSymbols is called with wrong tree -

MetalsInteractive.enclosingSymbols(path, pos, indexed) match
so problem is with
Interactive.pathTo(driver.openedTrees(uri), pos)(using driver.currentCtx)

I'm not sure what how that method work and what should be expected from it though.


Result for summonFrom()

Received request 'textDocument/definition - (206)'
Params: {
  "textDocument": {
    "uri": ".../A.scala"
  },
  "position": {
    "line": 8,
    "character": 10
  }
}
Tree

MetalsInteractive.scala:188 path: List(
  Block(
    stats = List(),
    expr = Match(
      selector = Thicket(trees = List()),
      cases = List(
        CaseDef(
          pat = Bind(
            name = given_Typeclass_Int,
            body = Typed(
              expr = Ident(name = _),
              tpt = AppliedTypeTree(tpt = Ident(name = Typeclass), args = List(Ident(name = Int)))
            )
          ),
          guard = Thicket(trees = List()),
          body = Block(stats = List(), expr = Literal(const = ( = 0)))
        ),
        CaseDef(
          pat = Ident(name = _),
          guard = Thicket(trees = List()),
          body = Block(stats = List(), expr = Literal(const = ( = 1)))
        )
      )
    )
  ),
  Typed(
    expr = Block(
      stats = List(),
      expr = Match(
        selector = Thicket(trees = List()),
        cases = List(
          CaseDef(
            pat = Bind(
              name = given_Typeclass_Int,
              body = Typed(
                expr = Ident(name = _),
                tpt = AppliedTypeTree(tpt = Ident(name = Typeclass), args = List(Ident(name = Int)))
              )
            ),
            guard = Thicket(trees = List()),
            body = Block(stats = List(), expr = Literal(const = ( = 0)))
          ),
          CaseDef(
            pat = Ident(name = _),
            guard = Thicket(trees = List()),
            body = Block(stats = List(), expr = Literal(const = ( = 1)))
          )
        )
      )
    ),
    tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Int)]
  ),
  DefDef(
    name = foo,
    paramss = List(),
    tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Int)],
    preRhs = Typed(
      expr = Block(
        stats = List(),
        expr = Match(
          selector = Thicket(trees = List()),
          cases = List(
            CaseDef(
              pat = Bind(
                name = given_Typeclass_Int,
                body = Typed(
                  expr = Ident(name = _),
                  tpt = AppliedTypeTree(
                    tpt = Ident(name = Typeclass),
                    args = List(Ident(name = Int))
                  )
                )
              ),
              guard = Thicket(trees = List()),
              body = Block(stats = List(), expr = Literal(const = ( = 0)))
            ),
            CaseDef(
              pat = Ident(name = _),
              guard = Thicket(trees = List()),
              body = Block(stats = List(), expr = Literal(const = ( = 1)))
            )
          )
        )
      ),
      tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Int)]
    )
  ),
  Template(
    constr = DefDef(
      name = <init>,
      paramss = List(List()),
      tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Unit)],
      preRhs = Thicket(trees = List())
    ),
    parentsOrDerived = List(
      Apply(
        fun = Select(
          qualifier = New(
            tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class Object)]
          ),
          name = <init>
        ),
        args = List()
      ),
      Ident(name = App)
    ),
    self = ValDef(
      name = _,
      tpt = SingletonTypeTree(ref = Ident(name = Main)),
      preRhs = Thicket(trees = List())
    ),
    preBody = List(
      DefDef(
        name = foo,
        paramss = List(),
        tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Int)],
        preRhs = Typed(
          expr = Block(
            stats = List(),
            expr = Match(
              selector = Thicket(trees = List()),
              cases = List(
                CaseDef(
                  pat = Bind(
                    name = given_Typeclass_Int,
                    body = Typed(
                      expr = Ident(name = _),
                      tpt = AppliedTypeTree(
                        tpt = Ident(name = Typeclass),
                        args = List(Ident(name = Int))
                      )
                    )
                  ),
                  guard = Thicket(trees = List()),
                  body = Block(stats = List(), expr = Literal(const = ( = 0)))
                ),
                CaseDef(
                  pat = Ident(name = _),
                  guard = Thicket(trees = List()),
                  body = Block(stats = List(), expr = Literal(const = ( = 1)))
                )
              )
            )
          ),
          tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Int)]
        )
      )
    )
  ),
  TypeDef(
    name = Main$,
    rhs = Template(
      constr = DefDef(
        name = <init>,
        paramss = List(List()),
        tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Unit)],
        preRhs = Thicket(trees = List())
      ),
      parentsOrDerived = List(
        Apply(
          fun = Select(
            qualifier = New(
              tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class Object)]
            ),
            name = <init>
          ),
          args = List()
        ),
        Ident(name = App)
      ),
      self = ValDef(
        name = _,
        tpt = SingletonTypeTree(ref = Ident(name = Main)),
        preRhs = Thicket(trees = List())
      ),
      preBody = List(
        DefDef(
          name = foo,
          paramss = List(),
          tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Int)],
          preRhs = Typed(
            expr = Block(
              stats = List(),
              expr = Match(
                selector = Thicket(trees = List()),
                cases = List(
                  CaseDef(
                    pat = Bind(
                      name = given_Typeclass_Int,
                      body = Typed(
                        expr = Ident(name = _),
                        tpt = AppliedTypeTree(
                          tpt = Ident(name = Typeclass),
                          args = List(Ident(name = Int))
                        )
                      )
                    ),
                    guard = Thicket(trees = List()),
                    body = Block(stats = List(), expr = Literal(const = ( = 0)))
                  ),
                  CaseDef(
                    pat = Ident(name = _),
                    guard = Thicket(trees = List()),
                    body = Block(stats = List(), expr = Literal(const = ( = 1)))
                  )
                )
              )
            ),
            tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Int)]
          )
        )
      )
    )
  )
)


Result for summonFrom { case ... }

Params: {
  "textDocument": {
    "uri": ".../A.scala"
  },
  "position": {
    "line": 8,
    "character": 10
  }
}
Tree

MetalsInteractive.scala:188 path: List(
  Ident(name = summonFrom),
  Apply(fun = Ident(name = summonFrom), args = List()),
  Block(stats = List(), expr = Apply(fun = Ident(name = summonFrom), args = List())),
  DefDef(
    name = foo,
    paramss = List(),
    tpt = TypeTree[dotty.tools.dotc.core.Types$PreviousErrorType@42cd1651],
    preRhs = Block(stats = List(), expr = Apply(fun = Ident(name = summonFrom), args = List()))
  ),
  Template(
    constr = DefDef(
      name = <init>,
      paramss = List(List()),
      tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Unit)],
      preRhs = Thicket(trees = List())
    ),
    parentsOrDerived = List(
      Apply(
        fun = Select(
          qualifier = New(
            tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class Object)]
          ),
          name = <init>
        ),
        args = List()
      ),
      Ident(name = App)
    ),
    self = ValDef(
      name = _,
      tpt = SingletonTypeTree(ref = Ident(name = Main)),
      preRhs = Thicket(trees = List())
    ),
    preBody = List(
      DefDef(
        name = foo,
        paramss = List(),
        tpt = TypeTree[dotty.tools.dotc.core.Types$PreviousErrorType@42cd1651],
        preRhs = Block(stats = List(), expr = Apply(fun = Ident(name = summonFrom), args = List()))
      )
    )
  ),
  TypeDef(
    name = Main$,
    rhs = Template(
      constr = DefDef(
        name = <init>,
        paramss = List(List()),
        tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class scala)),class Unit)],
        preRhs = Thicket(trees = List())
      ),
      parentsOrDerived = List(
        Apply(
          fun = Select(
            qualifier = New(
              tpt = TypeTree[TypeRef(ThisType(TypeRef(NoPrefix,module class lang)),class Object)]
            ),
            name = <init>
          ),
          args = List()
        ),
        Ident(name = App)
      ),
      self = ValDef(
        name = _,
        tpt = SingletonTypeTree(ref = Ident(name = Main)),
        preRhs = Thicket(trees = List())
      ),
      preBody = List(
        DefDef(
          name = foo,
          paramss = List(),
          tpt = TypeTree[dotty.tools.dotc.core.Types$PreviousErrorType@42cd1651],
          preRhs = Block(
            stats = List(),
            expr = Apply(fun = Ident(name = summonFrom), args = List())
          )
        )
      )
    )
  )
)

dos65 added a commit to dos65/dotty that referenced this issue Sep 12, 2022
Use the span of all tree instead of only cases.
This is needed for Metals: scalameta/metals#4366
@dos65
Copy link
Member

dos65 commented Sep 12, 2022

The issue is that summonFrom doesn't exist in after typer.
It's transformed into InlineMatch(EmptyTree, ...). We can match it back into summonFrom but we need to wait scala/scala3#16025. Right now the position isn't correct and Interactive.pathTo returns a set of different results instead of InlineMatch :: _

@tgodzik tgodzik added navigation Related to goto definition, find references, open symbol Scala 3 Generic ticket relating to Scala 3 presentation-compiler Something relating to the presentation compiler upstream-fix-needed Waiting on a fix upstream labels Sep 12, 2022
WojciechMazur added a commit to scala/scala3 that referenced this issue Sep 15, 2022
Use the span of all tree instead of only cases.
This is needed for Metals:
scalameta/metals#4366
mpollmeier pushed a commit to mpollmeier/dotty that referenced this issue Oct 16, 2022
Use the span of all tree instead of only cases.
This is needed for Metals: scalameta/metals#4366
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
navigation Related to goto definition, find references, open symbol presentation-compiler Something relating to the presentation compiler Scala 3 Generic ticket relating to Scala 3 upstream-fix-needed Waiting on a fix upstream
Projects
None yet
Development

No branches or pull requests

3 participants