Description
JavaFileObjects
violates StandardJavaFileManager
contract wrt toUri
:
The URI returned from
FileObject.toUri()
- must be absolute (have a schema), and
- must have a normalized path component which can be resolved without any process-specific context such as the current directory (file names must be absolute).
According to these rules, the following URIs, for example, are allowed:
file:///C:/Documents%20and%20Settings/UncleBob/BobsApp/Test.java
jar:///C:/Documents%20and%20Settings/UncleBob/lib/vendorA.jar!com/vendora/LibraryClass.class
Whereas these are not (reason in parentheses):
file:BobsApp/Test.java
(the file name is relative and depend on the current directory)jar:lib/vendorA.jar!com/vendora/LibraryClass.class
(the first half of the path depends on the current directory, whereas the component after ! is legal)Test.java
(this URI depends on the current directory and does not have a schema)jar:///C:/Documents%20and%20Settings/UncleBob/BobsApp/../lib/vendorA.jar!com/vendora/LibraryClass.class
(the path is not normalized)
— Source: http://docs.oracle.com/javase/7/docs/api/javax/tools/StandardJavaFileManager.html
The javadoc for JavaCompiler
gives an example of implementation for a string-based JavaFileObject
:
For example, here is how to define a file object which represent source code stored in a string:
/** * A file object used to represent source coming from a string. */ public class JavaSourceFromString extends SimpleJavaFileObject { /** * The source code of this "file". */ final String code; /** * Constructs a new JavaSourceFromString. * @param name the name of the compilation unit represented by this file object * @param code the source code for the compilation unit represented by this file object */ JavaSourceFromString(String name, String code) { super(URI.create("string:///" + name.replace('.','/') + Kind.SOURCE.extension), Kind.SOURCE); this.code = code; } @Override public CharSequence getCharContent(boolean ignoreEncodingErrors) { return code; } }
Note how they prefix the URI with "string:///"
(it's otherwise equivalent to what JavaFileObjects.forSourceString
does).
AFAICT, this is an issue only for forSourceString
(and forSourceLines
, which ultimately defer to forSourceString
), and forResource
when the resource is in a JAR (e.g. not if it's a file).