java.net.URISyntaxException - java

I have get this exception. but this exception is not reproduced again. I want to get the cause of this
Exception Caught while Checking tag in XMLjava.net.URISyntaxException:
Illegal character in opaque part at index 2:
C:\Documents and Settings\All Users\.SF\config\sd.xml
stacktrace net.sf.saxon.trans.XPathException.
Why this exception occured. How to deal with so it will not reproduce.

A valid URI does not contain backslashes, and if it contains a : then the characters before the first : must be a "protocol".
Basically "C:\Documents and Settings\All Users\.SF\config\sd.xml" is a pathname, and not a valid URI.
If you want to turn a pathname into a "file:" URI, then do the following:
File f = new File("C:\Documents and Settings\All Users\.SF\config\sd.xml");
URI u = f.toURI();
This is the simplest, and most reliable and portable way to turn a pathname into a valid URI in Java. It should work on Windows, Mac, Linux and any other platform that supports Java. (Other solutions that involve using string bashing on a pathname are not portable.)
But you need to realize that "file:" URIs have a number of caveats, as described in the javadocs for the File.toURI() method. For example, a "file:" URI created on one machine usually denotes a different resource (or no resource at all) on another machine.

The root cause for this is file path contains the forward slashes instead of backward slashes in windows.
Try like this to resolve the problem:
"file:" + string.replace("\\", "/");

You must have the string like so:
String windowsPath = file:/C:/Users/sizu/myFile.txt;
URI uri = new URI(windowsPath);
File file = new File(uri);
Usually, people do something like this:
String windowsPath = file:C:/Users/sizu/myFile.txt;
URI uri = new URI(windowsPath);
File file = new File(uri);
or something like this:
String windowsPath = file:C:\Users\sizu\myFile.txt;
URI uri = new URI(windowsPath);
File file = new File(uri);

It needs a complete uri with type/protocol
e.g
file:/C:/Users/Sumit/Desktop/s%20folder/SAMPLETEXT.txt
File file = new File("C:/Users/Sumit/Desktop/s folder/SAMPLETEXT.txt");
file.toURI();//This will return the same string for you.
I will rather use direct string to avoid creating extra file object.

I had the same "opaque" error while passing a URI on the command line to a script. This was on windows. I had to use forward slashes, NOT backslashes. This resolved it for me.

it doesn't like spaces as well and it has to be / instead of \ or `\ or //
zipFilePath = "C:/test/v";

Related

Is there a way to get the path of a File with "/" instead of "\"?

I am making an HTTP Server in Java so that (on start) it finds all files in a directory (and it's sub-directories) and adds them to the server. But when getting the path of a file and trying to give it to HttpServer.createContext(), it throws a java.lang.IllegalArgumentException: Illegal value for path or protocol. (with the string argument, say "\folder/index.html"). To get this value, I used
file.getParent().substring(24) + "/" + file.getName()
I used substring because I had to exclude the folder the web server is in. The illegal character is the backslash. I have tried extending File to change separator and separatorChar, but that only created 2 new variables. While using String.replace() didn't seem to have any effect. Is there a different method than File.getParent or File.getPath that I can use, or is there a way to use String.replace that I am not seeing?
EDIT:
String.replace() seems to be the best answer... But I am not completely sure how to use it.
EDIT 2: For some reason the backslash isn't showing up, so I changed it.
You have to use the java System.getProperty.
Notice that, in this context, "file.separator" is a key which we are
using to get this property from current system executing the java VM.
Insteady of using a slash (/), you should choose a platform agnostic file separator, as an example it should be:
String separator = System.getProperty("file.separator");
System.out.println(separator);
// unix / , windows \
Have a look at Paths.get(...)
Try Paths.get(".") // current working directory.
Or tell it, on which path it should start:
Use System.getProperty("user.dir"), for current loged in user, home directory.
String pathStr = "/";
Path homeDir = Paths.get(System.getProperty("user.dir"))
Getting from the user directory into the data directory: homeDir.get("data")
Path dataPath = Paths.get(System.getProperty("user.dir"));
File dataFile = dataPath.toFile();
Now use operations on dataFile, to check what files and directories there are, on that location of the file system.

Java - find jar file of class (or classes directory)

I can request the URL for the jar file or classes directory where Java loaded a class from:
Class clazz = ...
URL url = clazz.getProtectionDomain().getCodeSource().getLocation();
but how to correctly convert this to a File (or Path) - especially with respect to some characters of the path escaped in URLs? I've tried this:
String fileName = URLDecoder.decode(url.getFile(), "UTF-8");
File jarFileOrClassesDir = new File(fileName);
but this causes problems if there is a + inside the path (the + is replaced with a space).
but this causes problems if there is a + inside the path (the + is replaced with a space).
This is standar behavior of URLDecoder. See more information at JavaDoc [1], plus (+) is mentioned there as well.
Solution using Paths
Using Paths#get(URI) [2] should preserve all "special" symbols and you can pass directly URI which can be retrieved directly from URL using URL#toURI() [3].
So in summary:
final var filePath = Paths.get(url.toURI()); // We can extract any information from Path e.g. fileName.
shoud work as expected.
[1] https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/net/URLDecoder.html
[2] https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/nio/file/Paths.html#get(java.net.URI)
[3] https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/net/URL.html#toURI()

How Can I read text file in liferay?

I have tried to read a file from controller class with this code
ReadFile readFile = new ReadFile();
String text = readFile.readFile("\resources\testing.txt");
renderRequest.setAttribute("text", text);
I have fetched it from view.jsp as
<%
String content = (String)request.getAttribute("text");
%>
But I am getting file not found exception. What is the way to get file content.
In a Java string, \ starts an escape sequence and "\r" and "\t" are escaped characters. For example "\t" is a string with the tab character. If you literally need \t in a string, you'll have to escape the backslash
doSomething("\\resources\\testing.txt");
or just eliminate the hassle: Java operates well when you use the forward slash as directory separator
doSomething("/resources/testing.txt");
Note that this refers to a file in the root directory of whatever drive the current path is on, it might be C:\resources\testing.txt or D:\resources\testing.txt - unless your ReadFile implementation manipulates the path somehow (which I leave up to your judgement). You can test this independent of Liferay, just in a command line application. The exception gets thrown way before your jsp gets displayed (I've changed the tags to flag the relevance)
This is pure Java, completely independent of Liferay.
The problem is with your relative path of resources file (testing.txt), that needs to be absolute. And to create absolute path, first you would require, portletContext which you can get from request, as following:
MVC Portlet:
PortletContext portletContext = request.getPortletSession().getPortletContext();
Where request is either renderRequest / actionRequest object. While in JSF, you can get request from externalContext, as following:
JSF Portlet:
ExternalContext externalContext = FacesContext.getCurrentInstance().getExternalContext();
PortletRequest request = (PortletRequest) externalContext.getRequest();
PortletContext portletContext = request.getPortletSession().getPortletContext();
Also, as suggested by Olaf Kock, if you use \, you would require to escape it, otherwise use /. I prefer to use File.separator, as it returns slash as per OS (I think!).
String relativeFilePath = File.separator + "resources" + File.separator + "testing.txt";
Now, you can get absolute path using portletContext as,
String absoluteFilePath = portletContext.getRealPath(relativeFilePath);
And then, rest of your code goes, as:
ReadFile readFile = new ReadFile();
String text = readFile.readFile(absoluteFilePath);
renderRequest.setAttribute("text", text);
Since you're getting a FileNotFoundException, Are you sure you're pointing to the proper file route? Have you tried with the absolute path? What SO are you using? Because maybe the file separators ("\") are the cause of your problem.
HIH.
Regards.

Java File access - URI madness

I'm working with IBM OmniFind, with has a fun way of handling file paths. If you've got a path like this:
C:\temp\some §$% path\temp - Sho rtcut.lnk
It becomes to this sort of "URI" (that's what they call it...):
file:///C:/temp/some+%C2%A7%24%25+path/temp+-+Sho+rtcut.lnk
This clearly seems to be escaped with URLEncoder.encode. Normally, Java would build this sort of URI from the path above:
file:/C:/temp/some%20%C2%A7$%25%20path/temp%20-%20Sho%20rtcut.lnk
file:/C:/temp/some%20§$%25%20path/temp%20-%20Sho%20rtcut.lnk
Now I have a really hard time of transforming this sort of URL Encoded Path into something that would work for File handles. This sort of does the trick, although it seems like a very questionable workaround:
String path = "file:///C:/temp/some+%C2%A7%24%25+path/temp+-+Sho+rtcut.lnk";
URL url = new URL(path);
path = url.toExternalForm().replaceAll("[+]", "%20");
URI uri = new URI(path);
File file = new File(uri);
System.out.println(file.exists());
Is there any safe-ish way of transforming URL escaped file paths to valid URIs in Java?

File.mkdir is not working and I can't understand why

I've this brief snippet:
String target = baseFolder.toString() + entryName;
target = target.substring(0, target.length() - 1);
File targetdir = new File(target);
if (!targetdir.mkdirs()) {
throw new Exception("Errore nell'estrazione del file zip");
}
doesn't mattere if I leave the last char (that is usually a slash). It's done this way to work on both unix and windows. The path is actually obtained from the URI of the base folder. As you can see from baseFolder.toString() (baseFolder is of type URI and is correct). The base folder actually exists. I can't debug this because all I get is true or false from mkdir, no other explanations.The weird thing is that baseFolder is created as well with mkdir and in that case it works.
Now I'm under windows.
the value of target just before the creation of targetdir is "file:/C:/Users/dario/jCommesse/jCommesseDB"
if I cut and paste it (without the last entry) in windows explore it works...
The path you provide is not a file path, but a URI.
I suggest you try the following :
URI uri = new URI("file://c:/foo/bar");
File f = new File(uri).
It looks, to me, as if the "file:/" at the beginning is the problem... Try getAbsolutePath() instead of toString().
The File constructor taking a String expects a path name. A path name is not an URI.
Remove the file:/ from the front of the String (or better yet, use getPath() instead of toString()) to get to the path you need.

Categories

Resources