I am trying to make a synchronous request to the server using RequestFuture but it's not working . The same request when done using asynchronous works fine.
This is my code:
public void fetchModules(){
JSONObject response = null;
RequestQueue requestQueue = Volley.newRequestQueue(getContext());
RequestFuture<JSONObject> future = RequestFuture.newFuture();
JsonObjectRequest request = new JsonObjectRequest(Url.ALL_MODULES_URL,null,future,future);
requestQueue.add(request);
try {
response = future.get(3, TimeUnit.SECONDS); // Blocks for at most 10 seconds.
} catch (InterruptedException e) {
Log.d(TAG,"interupted");
} catch (ExecutionException e) {
Log.d(TAG,"execution");
} catch (TimeoutException e) {
e.printStackTrace();
}
Log.d(TAG,response.toString());
}
I am getting a nullpointerexception:
java.lang.NullPointerException: Attempt to invoke virtual method 'java.lang.String org.json.JSONObject.toString()' on a null object reference at com.maths.app.AllModules.fetchModules(AllModules.java:85) at com.maths.app.AllModules.onCreateView(AllModules.java:51) at android.support.v4.app.Fragment.performCreateView(Fragment.java:2080) at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1108) at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1290) at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:801) at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1677) at android.support.v4.app.FragmentManagerImpl$1.run(FragmentManager.java:536) at android.os.Handler.handleCallback(Handler.java:746) at android.os.Handler.dispatchMessage(Handler.java:95) at android.os.Looper.loop(Looper.java:148) at android.app.ActivityThread.main(ActivityThread.java:5443) at java.lang.reflect.Method.invoke(Native Method) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:728) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
it's returning a null response. How can I solve this?
We can use RxJava.
Lets assume that the fetchModules method returns JSONObject
In MainActivity
After researching this question myself, you CAN'T (at the moment of writing) do it in the main thread
I want Volley to do it in the main thread because I need to block until Volley finish getting response. And this is not possible, synchronous request on Volley must be in an async thread, not in the main thread.
The work around that I have done is, doing the subsequent codes inside the onResponse method of Volley request
tl;dr; You got deceived by the try-catch
Explanation: Because the
RequestFuture.get()
is probably running on the UI thread you are really getting ajava.util.concurrent.TimeoutException
behind the scenes. That is the default behaviour when the calls gets executed on the main thread.The try catch stops the app from crashing, nevertheless the response is still a null reference which crashes the app when you try to
Log
the result. If you comment the following line you will see that the app doesn't crash (there) anymore.Fix: Making the RequestFuture network call on another thread!
One way to do it:
The
AsyncTask
which will make the network call :Main Activity:
result:
Hope this helps
cheers!