Hello Android/Java coders!
So I recently got some weird errors when doing HTTP requests in my Android game Hamster Climb. I was trying to get the input stream from a HttpURLConnection but kept getting a FileNotFoundException even though the URL worked perfectly in my desktop browser. Here’s an example, without error catching stuff, of how the code could look like:
String user = getUser(); String url = "http://somesite.com/page?user=" + user; URL u = new URL(url); HttpURLConnection c = (HttpURLConnection) u.openConnection(); c.setDoInput(true); c.setDoOutput(true); c.connect(); InputStream is = c.getInputStream();
The problem was that at the last line the call to getInputStream generated a FileNotFoundException. I printed the URL that was used and tried it in the browser. Worked prefectly.
I managed to solve it though. The problem was that even though creating a URL object with the built URL string works, the URL might be broken. For example, if user is “Some guy” the url will contain a space which is not valid. Browsers solve this by automatically replacing the space with %20 which is what my browser did.
To solve this in code you use the URLEncoder class’ static method encode. This method takes a string and encodes it to a string that is ok to put in a URL. So replacing
String url = "http://somesite.com/page?user=" + user;
with
String url = "http://somesite.com/page?user=" + URLEncoder.encode(user, "UTF-8");
solves the problem when user contains illegal URL characters.
Hope this helps someone out there getting weird errors. 🙂
I had the same exact exception happening at my end.
Though the bug I found was a null value was being set for a request-header property of HttpURLConnection.
Maybe this helps someone.
nice
@rishabh,
which request-header property?
I am also getting this exception, but I have no characters in my URL string that would need encoding. can you tell me which property you had that was null?
thanks.
Hey Nate,
In my case, the K-V pair for a request property was “site-id” : “”
So if by mistake a null value was being passed, the server was not able to make a connection, and was throwing a FNFE.
The best practice states that:
* Check your request params, for valid K-V pairs.
* Check for a 200 OK response, before you perform a getInputStream on the connection object.
if (connection.getResponseCode() == HttpURLConnection.HTTP_OK) {
// valid response, retrieve your input stream
BufferedReader reader = new BufferedReader(new InputStreamReader(
connection.getInputStream(), “UTF-8”));
} else {
// something bad happened, debug from your server .
}
This is awesome thanks! Took me 2 hours to fix this
removing c.setDoOutput(true) worked for me. 🙂
Thanks 🙂
Thank you very much, very useful.
Something I want to add here. Different part of a URL has different encoding so you should not encode the whole URL with the same encoding. Only encode the unreliable part of the URL. Here is a stack overflow link to explain this: http://stackoverflow.com/questions/3286067/url-encoding-in-android
Oh nice. Thanks. 🙂
(Sorry for taking ages to accept the comment. 😦 )
I have the same issue, but it’s appear only in one of my emulator. When I clicked on link printed with error, site with that file was oppened.
OK. Problem solved. I had a manual proxy configuration set in settings of my emulator.