@@ -7,7 +7,7 @@ import _root_.scala.tools.nsc.reporters.ConsoleReporter
7
7
import _root_ .scala .tools .nsc .Settings
8
8
import xsbti ._
9
9
import xsbti .api .SourceAPI
10
- import sbt .IO .withTemporaryDirectory
10
+ import sbt .IO ._
11
11
import xsbti .api .ClassLike
12
12
import xsbti .api .Definition
13
13
import xsbti .api .Def
@@ -21,7 +21,7 @@ import ScalaCompilerForUnitTesting.ExtractedSourceDependencies
21
21
* Provides common functionality needed for unit tests that require compiling
22
22
* source code using Scala compiler.
23
23
*/
24
- class ScalaCompilerForUnitTesting (nameHashing : Boolean = false ) {
24
+ class ScalaCompilerForUnitTesting (nameHashing : Boolean , includeSynthToNameHashing : Boolean = false ) {
25
25
import scala .language .reflectiveCalls
26
26
27
27
/**
@@ -33,6 +33,15 @@ class ScalaCompilerForUnitTesting(nameHashing: Boolean = false) {
33
33
analysisCallback.apis(tempSrcFile)
34
34
}
35
35
36
+ /**
37
+ * Compiles given source code using Scala compiler and returns API representation
38
+ * extracted by ExtractAPI class.
39
+ */
40
+ def extractApisFromSrcs (reuseCompilerInstance : Boolean )(srcs : List [String ]* ): Seq [SourceAPI ] = {
41
+ val (tempSrcFiles, analysisCallback) = compileSrcs(srcs.toList, reuseCompilerInstance)
42
+ tempSrcFiles.map(analysisCallback.apis)
43
+ }
44
+
36
45
def extractUsedNamesFromSrc (src : String ): Set [String ] = {
37
46
val (Seq (tempSrcFile), analysisCallback) = compileSrcs(src)
38
47
analysisCallback.usedNames(tempSrcFile)
@@ -66,7 +75,7 @@ class ScalaCompilerForUnitTesting(nameHashing: Boolean = false) {
66
75
def extractDependenciesFromSrcs (srcs : List [Map [Symbol , String ]]): ExtractedSourceDependencies = {
67
76
val rawGroupedSrcs = srcs.map(_.values.toList)
68
77
val symbols = srcs.flatMap(_.keys)
69
- val (tempSrcFiles, testCallback) = compileSrcs(rawGroupedSrcs)
78
+ val (tempSrcFiles, testCallback) = compileSrcs(rawGroupedSrcs, reuseCompilerInstance = true )
70
79
val fileToSymbol = (tempSrcFiles zip symbols).toMap
71
80
72
81
val memberRefFileDeps = testCallback.sourceDependencies collect {
@@ -109,19 +118,31 @@ class ScalaCompilerForUnitTesting(nameHashing: Boolean = false) {
109
118
* useful to compile macros, which cannot be used in the same compilation run that
110
119
* defines them.
111
120
*
121
+ * The `reuseCompilerInstance` parameter controls whether the same Scala compiler instance
122
+ * is reused between compiling source groups. Separate compiler instances can be used to
123
+ * test stability of API representation (with respect to pickling) or to test handling of
124
+ * binary dependencies.
125
+ *
112
126
* The sequence of temporary files corresponding to passed snippets and analysis
113
127
* callback is returned as a result.
114
128
*/
115
- private def compileSrcs (groupedSrcs : List [List [String ]]): (Seq [File ], TestCallback ) = {
116
- withTemporaryDirectory { temp =>
117
- val analysisCallback = new TestCallback (nameHashing)
129
+ private def compileSrcs (groupedSrcs : List [List [String ]],
130
+ reuseCompilerInstance : Boolean ): (Seq [File ], TestCallback ) = {
131
+ // withTemporaryDirectory { temp =>
132
+ {
133
+ val temp = createTemporaryDirectory
134
+ val analysisCallback = new TestCallback (nameHashing, includeSynthToNameHashing)
118
135
val classesDir = new File (temp, " classes" )
119
136
classesDir.mkdir()
120
137
121
- // val (compiler, ctx) = prepareCompiler(classesDir, analysisCallback, classesDir.toString)
138
+ lazy val commonCompilerInstanceAndCtx = prepareCompiler(classesDir, analysisCallback, classesDir.toString)
122
139
123
140
val files = for ((compilationUnit, unitId) <- groupedSrcs.zipWithIndex) yield {
124
- val (compiler, ctx) = prepareCompiler(classesDir, analysisCallback, classesDir.toString)
141
+ // use a separate instance of the compiler for each group of sources to
142
+ // have an ability to test for bugs in instability between source and pickled
143
+ // representation of types
144
+ val (compiler, ctx) = if (reuseCompilerInstance) commonCompilerInstanceAndCtx else
145
+ prepareCompiler(classesDir, analysisCallback, classesDir.toString)
125
146
val run = compiler.newRun(ctx)
126
147
val srcFiles = compilationUnit.toSeq.zipWithIndex map {
127
148
case (src, i) =>
@@ -132,15 +153,15 @@ class ScalaCompilerForUnitTesting(nameHashing: Boolean = false) {
132
153
133
154
run.compile(srcFilePaths)
134
155
135
- srcFilePaths.foreach(f => new File (f).delete)
156
+ // srcFilePaths.foreach(f => new File(f).delete)
136
157
srcFiles
137
158
}
138
159
(files.flatten.toSeq, analysisCallback)
139
160
}
140
161
}
141
162
142
163
private def compileSrcs (srcs : String * ): (Seq [File ], TestCallback ) = {
143
- compileSrcs(List (srcs.toList))
164
+ compileSrcs(List (srcs.toList), reuseCompilerInstance = true )
144
165
}
145
166
146
167
private def prepareSrcFile (baseDir : File , fileName : String , src : String ): File = {
@@ -151,10 +172,6 @@ class ScalaCompilerForUnitTesting(nameHashing: Boolean = false) {
151
172
152
173
private def prepareCompiler (outputDir : File , analysisCallback : AnalysisCallback , classpath : String = " ." ) = {
153
174
val args = Array .empty[String ]
154
- object output extends SingleOutput {
155
- def outputDirectory : File = outputDir
156
- override def toString = s " SingleOutput( $outputDirectory) "
157
- }
158
175
159
176
import dotty .tools .dotc ._
160
177
import dotty .tools .dotc .core .Contexts ._
@@ -171,7 +188,7 @@ class ScalaCompilerForUnitTesting(nameHashing: Boolean = false) {
171
188
}
172
189
}
173
190
val ctx = (new ContextBase ).initialCtx.fresh.setSbtCallback(analysisCallback)
174
- driver.getCompiler(Array (" -classpath" , classpath, " -usejavacp" ), ctx)
191
+ driver.getCompiler(Array (" -classpath" , classpath, " -usejavacp" , " -d " , outputDir.getAbsolutePath ), ctx)
175
192
}
176
193
177
194
private object ConsoleReporter extends Reporter {
0 commit comments