如何将JDK中的类链接到scaladoc生成的doc?

我正在尝试将JDK中的类链接到scaladoc生成的doc中。 我使用了scaladoc 2.10.1的-doc-external-doc选项,但没有成功。

我正在使用-doc-external-doc:/usr/lib/jvm/java-7-openjdk-amd64/jre/lib/rt.jar#http://docs.oracle.com/javase/7/docs/api/ ,但我得到的链接如index.html#java.io.File而不是index.html?java/io/File.html 。 似乎此选项仅适用于scaladoc生成的doc。

我是否错过了scaladoc中的选项,还是应该填写function请求?

我已经配置sbt如下:

  scalacOptions in (Compile,doc) += "-doc-external-doc:/usr/lib/jvm/java-7-openjdk-amd64/jre/lib/rt.jar#http://docs.oracle.com/javase/7/docs/api" 

注意:我在即将发布的sbt 0.13中看到了Opts.doc.externalAPI util。 我认为一个很好的补充(不确定是否可能)将传递ModuleID而不是File 。 util会找出哪个文件对应于ModuleID

我使用sbt 0.13.5。

没有开箱即用的方法可以在scaladoc中使用Javadoc链接。 正如我的理解所说,这不是sbt的错,而是scaladoc的工作方式。 正如约什在评论中指出的那样你应该向斯卡拉多克报告。

然而,我提出了一个解决方法 – 对doc生成的scaladoc进行后处理,以便替换Java URL以形成正确的Javadoc链接。

文件scaladoc.sbt应放在sbt项目中,每当执行doc任务时,通过fixJavaLinksTask任务进行后处理fixJavaLinksTask启动。

注意有很多硬编码路径,所以要小心使用它( 也就是你认为合适的抛光)。

 import scala.util.matching.Regex.Match autoAPIMappings := true // builds -doc-external-doc apiMappings += ( file("/Library/Java/JavaVirtualMachines/jdk1.8.0_11.jdk/Contents/Home/jre/lib/rt.jar") -> url("http://docs.oracle.com/javase/8/docs/api") ) lazy val fixJavaLinksTask = taskKey[Unit]( "Fix Java links - replace #java.io.File with ?java/io/File.html" ) fixJavaLinksTask := { println("Fixing Java links") val t = (target in (Compile, doc)).value (t ** "*.html").get.filter(hasJavadocApiLink).foreach { f => println("fixing " + f) val newContent = javadocApiLink.replaceAllIn(IO.read(f), fixJavaLinks) IO.write(f, newContent) } } val fixJavaLinks: Match => String = m => m.group(1) + "?" + m.group(2).replace(".", "/") + ".html" val javadocApiLink = """\"(http://docs\.oracle\.com/javase/8/docs/api/index\.html)#([^"]*)\"""".r def hasJavadocApiLink(f: File): Boolean = (javadocApiLink findFirstIn IO.read(f)).nonEmpty fixJavaLinksTask <<= fixJavaLinksTask triggeredBy (doc in Compile) 

我接受了@ jacek-laskowski的回答并对其进行了修改,以避免使用硬编码的字符串,并且可以用于任何数量的Java库,而不仅仅是标准库。

编辑:现在使用sun.boot.class.path从运行时确定rt.jar的位置,并且不必进行硬编码。

您需要修改的唯一内容是map,我在下面称为externalJavadocMap

 import scala.util.matching.Regex import scala.util.matching.Regex.Match val externalJavadocMap = Map( "owlapi" -> "http://owlcs.github.io/owlapi/apidocs_4_0_2/index.html" ) /* * The rt.jar file is located in the path stored in the sun.boot.class.path system property. * See the Oracle documentation at http://docs.oracle.com/javase/6/docs/technotes/tools/findingclasses.html. */ val rtJar: String = System.getProperty("sun.boot.class.path").split(java.io.File.pathSeparator).collectFirst { case str: String if str.endsWith(java.io.File.separator + "rt.jar") => str }.get // fail hard if not found val javaApiUrl: String = "http://docs.oracle.com/javase/8/docs/api/index.html" val allExternalJavadocLinks: Seq[String] = javaApiUrl +: externalJavadocMap.values.toSeq def javadocLinkRegex(javadocURL: String): Regex = ("""\"(\Q""" + javadocURL + """\E)#([^"]*)\"""").r def hasJavadocLink(f: File): Boolean = allExternalJavadocLinks exists { javadocURL: String => (javadocLinkRegex(javadocURL) findFirstIn IO.read(f)).nonEmpty } val fixJavaLinks: Match => String = m => m.group(1) + "?" + m.group(2).replace(".", "/") + ".html" /* You can print the classpath with `show compile:fullClasspath` in the SBT REPL. * From that list you can find the name of the jar for the managed dependency. */ lazy val documentationSettings = Seq( apiMappings ++= { // Lookup the path to jar from the classpath val classpath = (fullClasspath in Compile).value def findJar(nameBeginsWith: String): File = { classpath.find { attributed: Attributed[File] => (attributed.data ** s"$nameBeginsWith*.jar").get.nonEmpty }.get.data // fail hard if not found } // Define external documentation paths (externalJavadocMap map { case (name, javadocURL) => findJar(name) -> url(javadocURL) }) + (file(rtJar) -> url(javaApiUrl)) }, // Override the task to fix the links to JavaDoc doc in Compile <<= (doc in Compile) map { target: File => (target ** "*.html").get.filter(hasJavadocLink).foreach { f => //println(s"Fixing $f.") val newContent: String = allExternalJavadocLinks.foldLeft(IO.read(f)) { case (oldContent: String, javadocURL: String) => javadocLinkRegex(javadocURL).replaceAllIn(oldContent, fixJavaLinks) } IO.write(f, newContent) } target } ) 

我使用的是SBT 0.13.8。