I have to build Javadoc from myCode.jar that contains both sources and class files. Can I do it without extracting the jar?
According to http://java.sun.com/j2se/1.5.0/docs/tooldocs/windows/javadoc.html#classpath I should be able to do so this way: C:\>javadoc -d docs -classpath myCode.jar net\kem\jmx\CacheManagerMBean.java
However, I get the following error:
javadoc: error - File not found: "net\kem\jmx\CacheManagerMBean.java"
[search path for source files: [myCode.jar]]
[search path for class files: [C:\Program Files\Java\jdk1.5.0_17\jre\lib\rt.jar, C:\Program Files\Java\jdk1.5.0_17\jre\lib\jsse.jar,
C:\Program Files\Java\jdk1.5.0_17\jre\lib\jce.jar, C:\Program Files\Java\jdk1.5.0_17\jre\lib\charsets.jar, C:\Program Files\Java\jd
k1.5.0_17\jre\lib\ext\dnsns.jar, C:\Program Files\Java\jdk1.5.0_17\jre\lib\ext\localedata.jar, C:\Program Files\Java\jdk1.5.0_17\jre
\lib\ext\sunjce_provider.jar, C:\Program Files\Java\jdk1.5.0_17\jre\lib\ext\sunpkcs11.jar, C:\Projects\RenderClusterController\WebCo
ntent\WEB-INF\lib\makoRenderJMX.jar]]
[done in 360 ms]
1 error
It seems, javadoc cannot find the source files within the jar. I'm confident that the sources are there.
Any suggestions?
Some first tests indicate it does not work (at least on OpenJDK 1.6.0_20, which I have here).
So, I looked into the source (browsable in a mercurial web-interface). Javadoc (in the version there, which may differ from the one I have here) uses quite some bits of Javac in its for the operation, and it looks like both are using the javax.tools.JavaFileManager
interface to implement access to their source files, specifically in the subinterface StandardJavaFileManager
.
This interface claims to be able to access zip file entries:
This file manager creates file objects representing regular files, zip file entries, or entries in similar file system based containers.
But here how it is used (in JavaDocTool.getRootDocImpl()
):
148 String name = it.head;
149 if (!docClasses && name.endsWith(".java") && new File(name).exists()) {
150 JavaFileObject fo = fm.getJavaFileObjects(name).iterator().next();
151 docenv.notice("main.Loading_source_file", name);
152 JCCompilationUnit tree = parse(fo);
153 classTrees.append(tree);
154 } else if (isValidPackageName(name)) {
155 names = names.append(name);
156 } else if (name.endsWith(".java")) {
157 docenv.error(null, "main.file_not_found", name);
158 } else {
159 docenv.error(null, "main.illegal_package_name", name);
160 }
The first case would apply in your call with a .java
file - but since it does not exist as a file in the file system (new File(name).exists()
returns false), this does not help, and you get instead the third case with a "file not found" error.
It looks like it could work when replacing this condition with a more suitable one (like !fm.getJavaFileObjects(name).isEmpty()
- provided the context is initialized with a JavaFileManager which in fact looks in jar/zip files, which I did not check now.
So, you'll have either to unpack your source jar, or patch your javac implementation (preferably contributing this to the main javac source).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With