@@ -2,7 +2,6 @@ package dotty.tools
2
2
package dotc
3
3
package typer
4
4
5
- import ast .untpd
6
5
import core ._
7
6
import Phases ._
8
7
import Contexts ._
@@ -56,18 +55,55 @@ class TyperPhase(addRootImports: Boolean = true) extends Phase {
56
55
JavaChecks .check(unit.tpdTree)
57
56
}
58
57
58
+ /** Report unused imports.
59
+ *
60
+ * If `-Yrewrite-imports`, emit patches instead.
61
+ * Patches are applied if `-rewrite` and no errors.
62
+ */
59
63
def emitDiagnostics (using Context ): Unit =
60
- ctx.usages.unused.foreach { (info, owner, selectors) =>
61
- import rewrites .Rewrites .patch
62
- import parsing .Parsers
63
- import util .SourceFile
64
- import ast .Trees .*
65
- def reportSelectors () = selectors.foreach(selector => report.warning(s " Unused import " , pos = selector.srcPos))
66
- if ctx.settings.YrewriteImports .value then
64
+ import ast .NavigateAST .untypedPath
65
+ import ast .Trees .*
66
+ import ast .untpd
67
+ import parsing .Parsers
68
+ import rewrites .Rewrites .patch
69
+ import util .SourceFile
70
+ def reportSelectors (sels : List [untpd.ImportSelector ]) = sels.foreach(sel => report.warning(s " Unused import " , pos = sel.srcPos))
71
+ // format the selectors without braces, as replacement text
72
+ def toText (sels : List [untpd.ImportSelector ]): String =
73
+ def selected (sel : untpd.ImportSelector ) =
74
+ if sel.isGiven then " given"
75
+ else if sel.isWildcard then " *"
76
+ else if sel.name == sel.rename then sel.name.show
77
+ else s " ${sel.name.show} as ${sel.rename.show}"
78
+ sels.map(selected).mkString(" , " )
79
+ // begin
80
+ val unused = ctx.usages.unused
81
+ if ctx.settings.YrewriteImports .value then
82
+ val byLocation = unused.groupBy((info, owner, selectors) => info.qualifier.sourcePos.withSpan(info.enclosingSpan))
83
+ byLocation.foreach { (enclosingPos, grouped) =>
84
+ val importText = enclosingPos.spanText
85
+ val lineSource = SourceFile .virtual(name = " import-line.scala" , content = importText)
86
+ val PackageDef (_, pieces) = Parsers .Parser (lineSource).parse(): @ unchecked
87
+ println(s " pieces are $pieces" )
88
+ grouped match {
89
+ case (info, owners, selectors) :: rest =>
90
+ println(s " info enclosing ${info.enclosingSpan} has qual ${info.qualifier.sourcePos}" )
91
+ println(s " untyped path from qual \n ${ untypedPath(info.qualifier.sourcePos.span).mkString(" \n " ) }" )
92
+ // println(s"untyped path\n${ untypedPath(info.enclosingSpan).mkString("\n") }")
93
+ case _ =>
94
+ println(s " I got nothing " )
95
+ }
96
+ }
97
+ /*
98
+ ctx.usages.unused.foreach { (info, owner, selectors) =>
99
+ println(s"PATCH enclosing ${info.enclosingSpan} in ${info.qualifier.sourcePos.withSpan(info.enclosingSpan).spanText}")
67
100
val src = ctx.compilationUnit.source
68
101
val infoPos = info.qualifier.sourcePos
69
- val lineSource = SourceFile .virtual(name = " import-line.scala" , content = infoPos.lineContent)
102
+ //val importText = infoPos.lineContent
103
+ val importText = infoPos.withSpan(info.enclosingSpan).spanText
104
+ val lineSource = SourceFile.virtual(name = "import-line.scala", content = importText)
70
105
val PackageDef(_, pieces) = Parsers.Parser(lineSource).parse(): @unchecked
106
+ println(s"ENCLOSING has ${pieces.length} parts")
71
107
// patch if there's just one import on the line, i.e., not import a.b, c.d
72
108
if pieces.length == 1 then
73
109
val retained = info.selectors.filterNot(selectors.contains)
@@ -85,19 +121,12 @@ class TyperPhase(addRootImports: Boolean = true) extends Phase {
85
121
patch(src, widened, toText(retained)) // try to remove braces
86
122
else
87
123
patch(src, selectorSpan, toText(retained))
88
- else
89
- reportSelectors()
90
- else
91
- reportSelectors()
92
- }
93
- // just the selectors, no need to add braces
94
- private def toText (retained : List [untpd.ImportSelector ])(using Context ): String =
95
- def selected (sel : untpd.ImportSelector ) =
96
- if sel.isGiven then " given"
97
- else if sel.isWildcard then " *"
98
- else if sel.name == sel.rename then sel.name.show
99
- else s " ${sel.name.show} as ${sel.rename.show}"
100
- retained.map(selected).mkString(" , " )
124
+ }
125
+ */
126
+ else
127
+ ctx.usages.unused.foreach { (info, owner, selectors) => reportSelectors(selectors) }
128
+ end emitDiagnostics
129
+
101
130
def clearDiagnostics ()(using Context ): Unit =
102
131
ctx.usages.clear()
103
132
0 commit comments