Unknown error while calling Web API from Android - android

i am trying to send a JSONObject as input parameter for a C# Web API with the following code
protected String doInBackground(JSONObject... companyInfo) {
try {
URL url;
URLConnection urlConn;
url = new URL(HOST_NAME + WEB_API_METHOD);
urlConn = url.openConnection();
urlConn.setDoInput(true);
urlConn.setDoOutput(true);
urlConn.setUseCaches(false);
urlConn.setRequestProperty("Content-Type", "application/json");
urlConn.setRequestProperty("Host", HOST_NAME);
urlConn.connect();
PrintWriter out = new PrintWriter(urlConn.getOutputStream());
out.print(companyInfo[0]);
out.close();
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(urlConn.getInputStream()));
StringBuilder stringBuilder = new StringBuilder();
String line;
while ((line = bufferedReader.readLine()) != null) {
stringBuilder.append(line).append("\n");
}
bufferedReader.close();
Log.i("companyInfo > ", stringBuilder.toString());
}
catch (Exception ex)
{
Log.e("Exception", ex.getLocalizedMessage());
}
return null;
}
When this is called, the method doesn't execute and when i try to catch the error, i don't get a meaningful message. it shows the URL name and thats it.
I am unable to find the issue and any help would be appreciated.
this is the error i got
java.io.FileNotFoundException: http://MY_FULL_URL
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.getInputStream(HttpURLConnectionImpl.java:238)
at com.fourtyninetons.NewCompanyActivity$saveCompanyProfile.doInBackground(NewCompanyActivity.java:103)
at com.fourtyninetons.NewCompanyActivity$saveCompanyProfile.doInBackground(NewCompanyActivity.java:70)
at android.os.AsyncTask$2.call(AsyncTask.java:295)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588)
at java.lang.Thread.run(Thread.java:818)
Lakshman.

As mentioned in the solution of this question, the problem is with the web api method and the backend database. Fiddler helped me solve the issue and the above code is working fine.
Useful Tip: When anyone gets this FileNotFoundExceptionuser POSTMAN or FIDDLER to execute the method and find for the errors.
Thank you everyone who attempted to solve this.

Related

HttpURLConnection getInputStream() not reading anything

I'm following an example of using the Reddit API in an Android app. I'm using Android Studio and Java. I have a link which returns a JSON object on a GET request (let's say http://www.reddit.com/r/dragonforce/.json), and the tutorial has this piece of code:
public static HttpURLConnection getConnection(String url){
System.out.println("URL: "+url);
HttpURLConnection hcon = null;
try {
hcon=(HttpURLConnection) new URL(url).openConnection();
hcon.setReadTimeout(30000); // Timeout at 30 seconds
hcon.setRequestProperty("User-Agent", "Alien V1.0");
} catch (MalformedURLException e) {
Log.e("getConnection()",
"Invalid URL: "+e.toString());
} catch (IOException e) {
Log.e("getConnection()",
"Could not connect: "+e.toString());
}
return hcon;
}
and
public static String readContents(String url){
HttpURLConnection hcon=getConnection(url);
if(hcon==null) return null;
try{
StringBuffer sb=new StringBuffer(8192);
String tmp="";
BufferedReader br=new BufferedReader(
new InputStreamReader(
hcon.getInputStream()
)
);
tmp = br.readLine();
while(tmp !=null) {
sb.append(tmp).append("\n");
tmp = br.readLine();
}
br.close();
return sb.toString();
}catch(IOException e){
Log.d("READ FAILED", e.toString());
return null;
}
}
I separated the tmp assignment for debug purposes. The problem is that nothing is read from the inputStream, and it returns an empty buffer to the JSONObject parser, resulting in JSONException end of input at character 0 of. I have user-permission in the Manifest for INTERNET, and the syntax for reading from the URL seems to be backed up by other sources on the internet, but it still seems something is amiss. Any help would be appreciated.
For anyone who is reading this down the line, the problem was that the URL in the tutorial was using HTTP instead of HTTPS, leading to a redirect response code and wasn't returning anything.

Send FCM messages from one device to other without server in Android

I know the risk of doing this.
But right now I only want to send message from one device to another device without any server.
Here is what I'm try.
JSONObject root = new JSONObject();
JSONObject notification = new JSONObject();
notification.put("body", messageText);
notification.put("title", username);
JSONObject data = new JSONObject();
data.put("senderToken", senderToken);
data.put("messageId", messageId);
root.put("notification", notification);
root.put("data", data);
root.put("to", receiverToken);
String postData = URLEncoder.encode(root.toString(),"UTF-8");
return openServerConnection(postData);
private String openServerConnection(String postData){
try {
URL url = new URL("https://fcm.googleapis.com/fcm/send");
HttpURLConnection httpURLConnection = (HttpURLConnection) url.openConnection();
httpURLConnection.setRequestProperty("Content-Type","application/json");
httpURLConnection.setRequestProperty("Authorization", "key=AAAAPQ4yGQM:APA9....1cW");
httpURLConnection.setRequestMethod("POST");
httpURLConnection.setDoInput(true);
httpURLConnection.setDoOutput(true);
OutputStream outputStream = httpURLConnection.getOutputStream();
BufferedWriter bufferedWriter = new BufferedWriter( new OutputStreamWriter(outputStream, "UTF-8") );
bufferedWriter.write(postData);
bufferedWriter.flush();
bufferedWriter.close();
outputStream.close();
InputStream inputStream = httpURLConnection.getInputStream();
BufferedReader bufferedReader = new BufferedReader( new InputStreamReader(inputStream, "iso-8859-1") );
StringBuilder result = new StringBuilder();
String line = "";
while( (line = bufferedReader.readLine()) != null ){
result.append(line);
}
bufferedReader.close();
inputStream.close();
httpURLConnection.disconnect();
return result.toString();
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
But I'm seeing an error.
W/System.err: java.io.FileNotFoundException: https://fcm.googleapis.com/fcm/send
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.getInputStream(HttpURLConnectionImpl.java:250)
W/System.err: at com.android.okhttp.internal.huc.DelegatingHttpsURLConnection.getInputStream(DelegatingHttpsURLConnection.java:210)
at com.android.okhttp.internal.huc.HttpsURLConnectionImpl.getInputStream(HttpsURLConnectionImpl.java)
at org.octabyte.zeem.InstantChat.SendMessage.openServerConnection(SendMessage.java:124)
W/System.err: at org.octabyte.zeem.InstantChat.SendMessage.doInBackground(SendMessage.java:74)
at org.octabyte.zeem.InstantChat.SendMessage.doInBackground(SendMessage.java:21)
at android.os.AsyncTask$2.call(AsyncTask.java:304)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
W/System.err: at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:243)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
W/System.err: at java.lang.Thread.run(Thread.java:761)
I'm not able to send any message, I checked my firebase token all are correct and server key also then what is the problem. Can you please let me know about this what I'm missing.
And second thing is I see the build in method already there for sending some kind of messages. But it's not working. What is the purpose of this method can you please let me know about this
Here is the code of this method. Can you please explain it.
RemoteMessage message = new RemoteMessage.Builder(getRegistrationToken())
.setMessageId(incrementIdAndGet())
.addData("message", "Hello")
.build();
FirebaseMessaging.getInstance().send(message);
What is this ????
Update
in documentation there described how you can send firebase messages using http request. right here Build App Server Send Requests can I use this method to send request from android device. Because in this method server key is not required. Can some body let me know about this is it possible or not ?
I test it and run your code. the problem is in postData You are encoding json data which case the problem. Just replace this line
String postData = URLEncoder.encode(root.toString(),"UTF-8");
// replace with
String postData = root.toString();

API call stopped working suddenly after few months

I am using below code to "GET" data using alpha Vantage API. It was working before for about 2 months then it suddenly stopped working. I don't see any change in JSON data.
private int retrievefromnet(int count,String symbol)
{
String temp;
String baseAddress = "http://www.alphavantage.co/query?function=TIME_SERIES_INTRADAY";
String apiKey = "J63P";
Uri Url = Uri.parse(baseAddress)
.buildUpon()
.appendQueryParameter("symbol", symbol)
.appendQueryParameter("interval", "1min")
.appendQueryParameter("apikey", apiKey)
.build();
Log.d("createList","built URL: " +Url.toString());
try {
url = new URL(Url.toString());
urlconnection = (HttpURLConnection) url.openConnection();
urlconnection.setRequestMethod("GET");
urlconnection.connect();
InputStream inputStream = urlconnection.getInputStream();
if (inputStream == null) {
return 0;
}
BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream));
Log.d("createList","here");
while ((temp = reader.readLine()) != null) {
DATA[count] += temp;
}
Log.d("unedited", DATA[count]);
} catch (IOException e) {
Log.e("createList", "Error in url ", e);
return 0;
}
return 1;
}
For extraction of data from JSON.
try {
String List = "Time Series (1min)";
JSONObject jsonObject = new JSONObject(DATA[count]);
jsonObject = jsonObject.getJSONObject(List);
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:00");
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis() - 34200000 );
String currtime = sdf.format(calendar.getTime());
Log.d("currtime",currtime);
jsonObject = jsonObject.getJSONObject(currtime);
return jsonObject.getString("4. close");
} catch (JSONException e) {
Log.e("createList", "Error in json");
}
Log says This:
D/createList: built URL: http://www.alphavantage.co/query?function=TIME_SERIES_INTRADAY&symbol=MSFT&interval=1min&apikey=J63P
D/libc: [NET] android_getaddrinfofornetcontext+,hn 19(0x7777772e616c70),sn(),hints(known),family 0,flags 1024, D/libc: [NET] android_getaddrinfo_proxy get netid:0
D/libc: [NET] android_getaddrinfo_proxy-, success
D/createList: here
E/createList: Error in json
Notice that the last log statement of try block in retreivefromnet is not showing nor is the log of the catch block.
DATA[] is a string array. It has been initialised before. Also, I checked that reader is null.
Help me find the issue.
EDit for Abhishek:
06-23 14:25:37.315 16817-16980/lcukerd.com.stocknotifier E/createList: Error in json
org.json.JSONException: End of input at character 0 of
at org.json.JSONTokener.syntaxError(JSONTokener.java:449)
at org.json.JSONTokener.nextValue(JSONTokener.java:97)
at org.json.JSONObject.<init>(JSONObject.java:156)
at org.json.JSONObject.<init>(JSONObject.java:173)
at lcukerd.com.stocknotifier.MainActivity$PlaceholderFragment$createList.workonJson(MainActivity.java:596)
at lcukerd.com.stocknotifier.MainActivity$PlaceholderFragment$createList.doInBackground(MainActivity.java:404)
at lcukerd.com.stocknotifier.MainActivity$PlaceholderFragment$createList.doInBackground(MainActivity.java:376)
at android.os.AsyncTask$2.call(AsyncTask.java:295)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588)
at java.lang.Thread.run(Thread.java:818)
You are having JSON parsing issue. It is better to use GSON library to parse JSON.
EX:
Gson gson = new Gson();
YOUR_OBJECT response = gson.fromJson("your_json_string", YOUR_OBJECT.class);
You can use online tool to create java object from json.
EX: http://www.jsonschema2pojo.org/
TRY THIS:
public int retrievefromnet(int count, String symbol) {
String temp;
String baseAddress = "https://www.alphavantage.co/query?function=TIME_SERIES_INTRADAY";
String apiKey = "J63P";
Uri Url = Uri.parse(baseAddress)
.buildUpon()
.appendQueryParameter("symbol", symbol)
.appendQueryParameter("interval", "1min")
.appendQueryParameter("apikey", apiKey)
.build();
try {
URL url = new URL(Url.toString());
HttpURLConnection urlconnection = (HttpURLConnection) url.openConnection();
urlconnection.setRequestMethod("GET");
urlconnection.connect();
InputStream inputStream = urlconnection.getInputStream();
if (inputStream == null) {
return 0;
}
BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream));
Log.d("createList", "here");
String responseStr = "";
while ((temp = reader.readLine()) != null) {
responseStr += temp;
}
Log.d("unedited", responseStr);
} catch (IOException e) {
Log.e("createList", "Error in url ", e);
return 0;
}
return 1;
}
To find the issue use this code e.printStackTrace(); in your catch block and share the logs along with the stack trace of the Exception object
it seems to be that the format of the content of the json data has changed, have you check the json content, it have been modified. Could you compare a good json processed before with this new?
Sorry for my english
It was simple. I just needed to replace HTTP with HTTPS. AlphaVantage might have changed something that's why it worked earlier but not now. Everything working fine now.

HttpURLConnection response missing Status Line (ProtocolException)

I currently am trying to make a request (With HttpURLConnection) to an IIS server that will bounce me with redirects until the target destination.
The issue : java.net.ProtocolException: Unexpected status line: <html><head><title>Object moved</title></head><body>
This happens when urlConnection.getInputStream() is called (or urlConnection.getResponseCode(), which calls it).
I have seen numerous cases where the issue is simply a misconfigured server, but in this case, making a request from Chrome while faking an Android user agent yields the expected result.
Furthermore, the server is an ancient one, that has never been the source of problem, and is configured in the same way as one used in a production environnement.
Reaching another redirecting webpage works fine (Tested with https://com.google/, 2 redirections), and reaching a non-redirecting webpage on the server poses no problem.
I have been looking for two days, and have made no progress. ANY help would be appreciated.
The code that is currently used :
StringBuilder builder = new StringBuilder();
HttpsURLConnection urlConnection = null;
try {
URL url = new URL(urlStrings[0]);
urlConnection = (HttpsURLConnection) url.openConnection();
LogHelper.Log(getBaseContext(), "Request on URL :\n\"" + url + "\"");
urlConnection.setRequestMethod("GET");
urlConnection.setReadTimeout(10000);
urlConnection.setConnectTimeout(15000);
urlConnection.setRequestProperty("Accept","*/*");
urlConnection.setDoOutput(false);
urlConnection.setDoInput(true);
urlConnection.setInstanceFollowRedirects(true);
urlConnection.setUseCaches(false);
CookieManager cookieManager = new CookieManager();
cookieManager.setCookiePolicy(CookiePolicy.ACCEPT_ALL);
CookieHandler.setDefault(cookieManager);
urlConnection.connect();
int status = urlConnection.getResponseCode();
LogHelper.Log(getBaseContext(), "Status code is \"" + status + "\"");
if (!url.equals(urlConnection.getURL())) {
LogHelper.Log(getBaseContext(), "URL after redirection is :\n\"" + urlConnection.getURL() + "\"");
}
switch (status/100) {
case 1:
case 2:
case 3:
InputStream stream = urlConnection.getInputStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(stream));
String line;
while ((line = reader.readLine()) != null) {
builder.append(line).append("\n");
}
reader.close();
break;
case 4:
case 5:
InputStream errorStream = urlConnection.getErrorStream();
BufferedReader errorReader = new BufferedReader(new InputStreamReader(errorStream));
String errorLine;
while ((errorLine = errorReader.readLine()) != null) {
builder.append(errorLine).append("\n");
}
errorReader.close();
throw new Exception(builder.toString());
default:
throw new Exception("Unknown status code: " + status);
}
} catch (Exception e) {
LogHelper.Log(getBaseContext(), e);
} finally {
if (urlConnection != null) {
urlConnection.disconnect();
}
}
return builder.toString();
The resulting error :
java.net.ProtocolException: Unexpected status line: <html><head><title>Object moved</title></head><body>
at com.android.okhttp.internal.http.StatusLine.parse(StatusLine.java:54)
at com.android.okhttp.internal.http.HttpConnection.readResponse(HttpConnection.java:239)
at com.android.okhttp.internal.http.HttpTransport.readResponseHeaders(HttpTransport.java:104)
at com.android.okhttp.internal.http.HttpEngine.readNetworkResponse(HttpEngine.java:1120)
at com.android.okhttp.internal.http.HttpEngine.readResponse(HttpEngine.java:951)
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.execute(HttpURLConnectionImpl.java:482)
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.getResponse(
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.getResponseCode(
at com.android.okhttp.internal.huc.DelegatingHttpsURLConnection.getResponseCode(
at com.android.okhttp.internal.huc.HttpsURLConnectionImpl.getResponseCode(
at com.pushmanager.clientmdm.activities.RegistrationView$1$2.doInBackground(
at com.pushmanager.clientmdm.activities.RegistrationView$1$2.doInBackground(
at android.os.AsyncTask$2.call(AsyncTask.java:295)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588)
at java.lang.Thread.run(Thread.java:818)
Turns out, this behavior was caused because of a \n character in the URL string.
I have no idea how okhttp managed this result, but with the character removed, the problem disappeared.

AsyncTask DoInBackground downloading Google Spreadsheets Data Returning Null?

Here is the code:
#Override
public String doInBackground(String... params)
{
try
{
URL url = new URL("http://spreadsheets.google.com/tq?key=BLAHBLOAHBLAH");
HttpURLConnection httpURLConnection = (HttpURLConnection) url.openConnection(); //Cast HttpUrlConnection because URL does not contain methods available to url, creates object
httpURLConnection.setRequestMethod("GET"); //Request data from source
httpURLConnection.setDoInput(true);
httpURLConnection.connect(); //Object actually connects, connect() invoked by getInputStream() etc.
//Reads data from network stream
InputStream inputStream = httpURLConnection.getInputStream();
//Rather than read one character at a time from the network or disk, BufferedReader reads a larger block at a time
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
//Used to create mutable string e.g. append()
StringBuilder stringBuilder = new StringBuilder();
String line = "";
//Change stream data to StringBuilder data
while ((line = bufferedReader.readLine()) != null)
{
stringBuilder.append(line + "\n");
}
String result = stringBuilder.toString();
bufferedReader.close();
inputStream.close();
httpURLConnection.disconnect();
return result;
}
catch(IOException e)
{
e.printStackTrace();
}
return null;
}
I'm basically downloading the JSON data from Google Spreadsheets, but the result returned from the doInBackground function continues to return some sort of a null object reference. What does this mean?...
EDIT*
Here is my logcat:
07-28 12:41:30.289 3796-3891/com.example.steven.app E/AndroidRuntime: FATAL EXCEPTION: AsyncTask #2
Process: com.example.steven.app, PID: 3796
java.lang.RuntimeException: An error occurred while executing doInBackground()
at android.os.AsyncTask$3.done(AsyncTask.java:309)
at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:354)
at java.util.concurrent.FutureTask.setException(FutureTask.java:223)
at java.util.concurrent.FutureTask.run(FutureTask.java:242)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588)
at java.lang.Thread.run(Thread.java:818)
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.app.AlertDialog.setMessage(java.lang.CharSequence)' on a null object reference
at com.example.steven.database.DownloadGS.doInBackground(DownloadGS.java:95)
at com.example.steven.database.DownloadGS.doInBackground(DownloadGS.java:49)
at android.os.AsyncTask$2.call(AsyncTask.java:295)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234) 
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113) 
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588) 
at java.lang.Thread.run(Thread.java:818) 
Picture of what is actually being stored inside String result...
My problem was:
URL url = new URL("http://spreadsheets.google.com/tq?key=BLAHBLOAHBLAH");
I found out that by reading here:
URLConnection Doesn't Follow Redirect
the setFollowRedirect and setInstanceFollowRedirects only work automatically when the redirected protocol is same . ie from http to http and https to https. (Shalvika)
I changed the statement to:
URL url = new URL("https://spreadsheets.google.com/tq?key=BLAHBLOAHBLAH");
Your code looks fine, the problem is that you are not allowed to get data from that URL.
On hitting this URL "http://spreadsheets.google.com/tq?key=BLAHBLOAHBLAH"
I am getting following response, so i guess you are getting access denied from server.
google.visualization.Query.setResponse (
{
"version": "0.6",
"status": "error",
"errors": [
{
"reason": "access_denied",
"message": "Access denied",
"detailed_message": "Access denied"
}]
}
)

Categories

Resources