From b753b150d9dc15bdac1addd2ee674370b6a0afba Mon Sep 17 00:00:00 2001 From: Josh Suereth Date: Fri, 27 Feb 2015 19:11:30 -0500 Subject: [PATCH] First cut at unifying new JavaTool interface with Doc usage. --- .../sbt/compiler/javac/JavaCompiler.scala | 16 ++++++++++++-- .../compiler/javac/JavaCompilerAdapter.scala | 4 ++-- .../actions/src/main/scala/sbt/Compiler.scala | 1 + main/actions/src/main/scala/sbt/Doc.scala | 21 +++++++++++++++++++ main/src/main/scala/sbt/Defaults.scala | 9 ++++++-- 5 files changed, 45 insertions(+), 6 deletions(-) diff --git a/compile/src/main/scala/sbt/compiler/javac/JavaCompiler.scala b/compile/src/main/scala/sbt/compiler/javac/JavaCompiler.scala index 8ea1be070..229ed083e 100644 --- a/compile/src/main/scala/sbt/compiler/javac/JavaCompiler.scala +++ b/compile/src/main/scala/sbt/compiler/javac/JavaCompiler.scala @@ -18,6 +18,8 @@ import xsbti.{ Severity, Reporter } sealed trait JavaTools { /** The raw interface of the java compiler for direct access. */ def compiler: JavaTool + /** The raw interface for javadoc for direct access. */ + def javadoc: JavaTool /** * This will run a java compiler. * @@ -49,6 +51,8 @@ sealed trait JavaTools { sealed trait IncrementalCompilerJavaTools extends JavaTools { /** An instance of the java Compiler for use with incremental compilation. */ def xsbtiCompiler: xsbti.compile.JavaCompiler + /** An instance of javadoc for use with incremental compilation or other tasks. */ + def xsbtiJavadoc: xsbti.compile.JavaCompiler } /** Factory methods for getting a java toolchain. */ object JavaTools { @@ -56,8 +60,10 @@ object JavaTools { def apply(c: JavaCompiler, docgen: Javadoc): JavaTools = new JavaTools { override def compiler = c + override def javadoc = docgen def compile(sources: Seq[File], options: Seq[String])(implicit log: Logger, reporter: Reporter): Boolean = c.run(sources, options) + def doc(sources: Seq[File], options: Seq[String])(implicit log: Logger, reporter: Reporter): Boolean = docgen.run(sources, options) } @@ -86,7 +92,9 @@ object JavaTools { val delegate = apply(compiler, doc) new IncrementalCompilerJavaTools { val xsbtiCompiler = new JavaCompilerAdapter(delegate.compiler, instance, cpOptions) + val xsbtiJavadoc = new JavaCompilerAdapter(delegate.javadoc, instance, cpOptions) def compiler = delegate.compiler + def javadoc = delegate.javadoc def compile(sources: Seq[File], options: Seq[String])(implicit log: Logger, reporter: Reporter): Boolean = delegate.compile(sources, options) def doc(sources: Seq[File], options: Seq[String])(implicit log: Logger, reporter: Reporter): Boolean = @@ -117,7 +125,9 @@ sealed trait JavaTool { } /** Interface we use to compile java code. This is mostly a tag over the raw JavaTool interface. */ -trait JavaCompiler extends JavaTool {} +trait JavaCompiler extends JavaTool { + override def toString = "javac" +} /** Factory methods for constructing a java compiler. */ object JavaCompiler { /** Returns a local compiler, if the current runtime supports it. */ @@ -133,7 +143,9 @@ object JavaCompiler { } /** Interface we use to document java code. This is a tag over the raw JavaTool interface. */ -trait Javadoc extends JavaTool {} +trait Javadoc extends JavaTool { + override def toString = "javadoc" +} /** Factory methods for constructing a javadoc. */ object Javadoc { /** Returns a local compiler, if the current runtime supports it. */ diff --git a/compile/src/main/scala/sbt/compiler/javac/JavaCompilerAdapter.scala b/compile/src/main/scala/sbt/compiler/javac/JavaCompilerAdapter.scala index 7ee67543a..c2d37ceac 100644 --- a/compile/src/main/scala/sbt/compiler/javac/JavaCompilerAdapter.scala +++ b/compile/src/main/scala/sbt/compiler/javac/JavaCompilerAdapter.scala @@ -24,7 +24,7 @@ class JavaCompilerAdapter(delegate: JavaTool, scalaInstance: xsbti.compile.Scala override final def compileWithReporter(sources: Array[File], classpath: Array[File], output: Output, options: Array[String], reporter: Reporter, log: xsbti.Logger): Unit = { val target = output match { case so: SingleOutput => so.outputDirectory - case mo: MultipleOutput => throw new RuntimeException("Javac doesn't support multiple output directories") + case mo: MultipleOutput => throw new RuntimeException(delegate + " doesn't support multiple output directories") } val args = commandArguments(Seq(), classpath, target, options, log) // We sort the sources for deterministic results. @@ -32,7 +32,7 @@ class JavaCompilerAdapter(delegate: JavaTool, scalaInstance: xsbti.compile.Scala if (!success) { // TODO - Will the reporter have problems from Scalac? It appears like it does not, only from the most recent run. // This is because the incremental compiler will not run javac if scalac fails. - throw new CompileFailed(args.toArray, "javac returned nonzero exit code", reporter.problems()) + throw new CompileFailed(args.toArray, delegate + " returned nonzero exit code", reporter.problems()) } } private[this] def commandArguments(sources: Seq[File], classpath: Seq[File], outputDirectory: File, options: Seq[String], log: Logger): Seq[String] = diff --git a/main/actions/src/main/scala/sbt/Compiler.scala b/main/actions/src/main/scala/sbt/Compiler.scala index 6aebcc0ec..c81dd8c1f 100644 --- a/main/actions/src/main/scala/sbt/Compiler.scala +++ b/main/actions/src/main/scala/sbt/Compiler.scala @@ -31,6 +31,7 @@ object Compiler { case x: JavaToolWithNewInterface => Some(x.newJavac) case _ => None } + } /** The previous source dependency analysis result from compilation. */ final case class PreviousAnalysis(analysis: Analysis, setup: Option[CompileSetup]) diff --git a/main/actions/src/main/scala/sbt/Doc.scala b/main/actions/src/main/scala/sbt/Doc.scala index 822b14565..aa7bf29b6 100644 --- a/main/actions/src/main/scala/sbt/Doc.scala +++ b/main/actions/src/main/scala/sbt/Doc.scala @@ -14,6 +14,7 @@ import sbinary.DefaultProtocol.FileFormat import Cache.{ defaultEquiv, hConsCache, hNilCache, seqCache, seqFormat, streamFormat, StringFormat, UnitFormat, wrapIn } import Tracked.{ inputChanged, outputChanged } import FilesInfo.{ exists, hash, lastModified } +import xsbti.compile.SingleOutput object Doc { import RawCompileLike._ @@ -21,11 +22,31 @@ object Doc { scaladoc(label, cache, compiler, Seq()) def scaladoc(label: String, cache: File, compiler: AnalyzingCompiler, fileInputOptions: Seq[String]): Gen = cached(cache, fileInputOptions, prepare(label + " Scala API documentation", compiler.doc)) + + @deprecated("Use new sbt.compiler.javac.* interfaces", "0.13.8") def javadoc(label: String, cache: File, doc: sbt.compiler.Javadoc): Gen = javadoc(label, cache, doc, Seq()) + @deprecated("Use new sbt.compiler.javac.* interfaces", "0.13.8") def javadoc(label: String, cache: File, doc: sbt.compiler.Javadoc, fileInputOptions: Seq[String]): Gen = cached(cache, fileInputOptions, prepare(label + " Java API documentation", filterSources(javaSourcesOnly, doc.doc))) + // TODO - These new javadoc methods are somewhat gross, like their predecessors. We should directly use the Javadoc interface. + def javadocWithIncrementalConfig(label: String, cache: File, doc: xsbti.compile.JavaCompiler, fileInputOptions: Seq[String]): Gen = { + + def gen(sources: Seq[File], classpath: Seq[File], outputDir: File, options: Seq[String], maximumErrors: Int, log: Logger): Unit = { + //doc.run(sources, args) + // TODO - Construct logger reporter + object output extends SingleOutput { + def outputDirectory: File = outputDir + override def toString = s"SingleOutput($outputDirectory)" + } + val reporter = new LoggerReporter(maximumErrors, log) + doc.compileWithReporter(sources.toArray, classpath.toArray, output, options.toArray, reporter, log) + reporter.printSummary() + } + cached(cache, fileInputOptions, prepare(label + " Java API documentation", filterSources(javaSourcesOnly, gen))) + } + val javaSourcesOnly: File => Boolean = _.getName.endsWith(".java") @deprecated("Use `scaladoc`", "0.13.0") diff --git a/main/src/main/scala/sbt/Defaults.scala b/main/src/main/scala/sbt/Defaults.scala index 968ef1960..2fec38367 100755 --- a/main/src/main/scala/sbt/Defaults.scala +++ b/main/src/main/scala/sbt/Defaults.scala @@ -750,8 +750,13 @@ object Defaults extends BuildCommon { (sOpts ++ Opts.doc.externalAPI(xapis), // can't put the .value calls directly here until 2.10.2 Doc.scaladoc(label, s.cacheDirectory / "scala", cs.scalac.onArgs(exported(s, "scaladoc")), fiOpts)) else if (hasJava) - (jOpts, - Doc.javadoc(label, s.cacheDirectory / "java", cs.javac.onArgs(exported(s, "javadoc")), fiOpts)) + cs.newJavac match { + case Some(jc) => + (jOpts, + Doc.javadocWithIncrementalConfig(label, s.cacheDirectory / "java", jc.xsbtiJavadoc, fiOpts)) + case _ => + (jOpts, Doc.javadoc(label, s.cacheDirectory / "java", cs.javac.onArgs(exported(s, "javadoc")), fiOpts)) + } else (Nil, RawCompileLike.nop) runDoc(srcs, cp, out, options, maxErrors.value, s.log)