Volley String cannot be converted to JSONObject - java

I'm always getting the following error as long as i put a array into Params. Even after converting to String it still gives that error. The code works fine without the contactlist array inside it. Any idea?
Error
com.android.volley.ParseError: org.json.JSONException: Value Created
of type java.lang.String cannot be converted to JSONObject
Sample response:
{
"username": "test2",
"lists": [
"contact_0",
"contact_1",
"contact_2",
"contact_3",
"contact_4",
"contact_5",
"contact_6",
"contact_7",
"contact_8",
"contact_9"
]
}
ArrayList<String> contactList = new ArrayList<String>();
public String joinInfo;
Cursor phones = getContentResolver().query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, null,null,null, null);
while (phones.moveToNext())
{
String name=phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME));
String phoneNumber = phones.getString(phones.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
System.out.println("name : " + name + ", ID : " + phoneNumber);
joinInfo = name;
contactList.add(joinInfo);
}
phones.close();
RequestQueue rq = Volley.newRequestQueue(this);
JSONObject params = new JSONObject();
try {
params.put("username", "test2");
params.put("lists", contactList.toString()); // When i change this to simply "test" a string, it works fine.
Log.d("PANDA", contactList.toString());
} catch (JSONException e) {
e.printStackTrace();
}
JsonObjectRequest jsonObjReq = new JsonObjectRequest(Request.Method.POST,
"http://postcatcher.in/catchers/55521f03f708be0300001d28", params, //Not null.
new Response.Listener<JSONObject>() {
#Override
public void onResponse(JSONObject response) {
Log.d("PANDA", response.toString());
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
VolleyLog.d("PANDA", "Error: " + error.getMessage());
Log.d("PANDA", error.toString());
}
});
// Adding request to request queue
rq.add(jsonObjReq);

PostCatcher although allowing us to post requests, its response is basically a plain string "Created" and not in Json format. As such our client code is not able to ascertain it and throws error. One thing is even without ArrayList object that is with plain (String, String) K,V pair also it would fail.
You can verify it if you try sending request through Advanced Rest Client (see attached)

Related

Android Volley get request, my onResponse never gets called

I know this question has been asked a few times and i have tried all the solutions however, nothing seems to work. My method:
public static LocationGeoData getLocationGeoData(Location location){
RequestQueue requestQueue = Volley.newRequestQueue(MyApplication.getAppContext());
Date dateNow = new Date();
SimpleDateFormat fmt = new SimpleDateFormat("yyyy.MM.dd");
String url = "MYCORRECTURL";
Log.d("geoData", "In getGeoData " + url); // this is called and logs
JsonObjectRequest request = new JsonObjectRequest(Request.Method.GET, url,
null,
new Response.Listener<JSONObject>() {
#Override
public void onResponse(JSONObject response) {
Log.d("geoData", "inside the response");// this never gets called
try {
JSONObject jsonObject = response.getJSONObject("data");
for(int i = 0; i <jsonObject.length(); i++){
JSONObject heading = jsonObject;
if(heading.getString("field-value").equals("field-value")){
JSONObject totIntensity = heading.getJSONObject("total-intensity");
JSONObject declination = heading.getJSONObject("declination");
JSONObject inclination = heading.getJSONObject("inclination");
int totalIntensity = totIntensity.getInt("value");
double declinationValue = declination.getDouble("value");
double inclinationValue = inclination.getDouble("value");
locationGeoData = new LocationGeoData(totalIntensity, declinationValue, inclinationValue);
}
}
} catch (JSONException e) {
Log.d("geoData", "Error recorded");//never called
e.printStackTrace();
}
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.d("geoData", "Error recorded");// never called
}
});
requestQueue.add(request);
return locationGeoData;
}
The second Log message inside the response never gets called, i get no error messages, my url works and i can see the JsonOBject in the browser when tested, but the response is never called in my method. Can anyone advise me what i am doing wrong?

How to access the json objects using volley

this is the api response i ma accessing the json object and setting the textview of uuid in text view but nothing happen
please suggest code for accessing json object from api response
{
"success":true,
"data {
"serial_key_id":"75",
"order_id":"0",
"product_id":"0",
"serial_key":"WURYFO",
"valid_till":null,
"limit":"0",
"uuid":"",
"used":false
}
}
private void jsonobject() {
String url = "http://mylocalpay.com/?serial_key_api=1&coupon=WURYFO";
JsonObjectRequest jsonObjectRequest = new JsonObjectRequest
(Request.Method.GET, url, null, new Response.Listener<JSONObject>() {
#Override
public void onResponse(JSONObject response) {
Log.i("msg", "response" + response);
try {
JSONObject success = response.getJSONObject("success");
JSONObject data = response.getJSONObject("data");
String serial_key_id = data.getString("serial_key_id");
String order_id = data.getString("order_id");
String product_id = data.getString("product_id");
String serial_key = data.getString("serial_key");
String limit = data.getString("limit");
String uuid = data.getString("uuid");
boolean used = data.getBoolean("used");
JSONObject valid_till = data.getJSONObject("valid_till");
textView.setText(uuid);
System.out.println(serial_key);
} catch (JSONException e) {
e.printStackTrace();
}
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
// TODO: Handle error
}
});
}
}
You need to parse this JSON into a java object. You could write your own code to do this (which is a very large undertaking) or you could use Googles GSON library.
GSON GitHub page
You can use this library as so
Gson gson = new Gson();
String jsonInString = "{'serial_key_id' : '75'}";
YourClass yourClass = gson.fromJson(jsonInString, YourClass.class);

How to POST parameters using JSONArrayRequest in Volley - (ERROR string cannot be converted to jsonarray)

This question may look like a duplicate(it is NOT), but I am stuck with this JSONException error:
Value die of type java.lang.String cannot be converted to JSONArray.
I'm using JsonArrayRequest of Volley to get jsonarray from a server. My JsonArrayRequest is throwing the above error, as i want to post a string to the server and receive jsonarray as a response. Below is my code:
JsonArrayRequest jsonReq = new JsonArrayRequest(Request.Method.POST,
URL, null, new Response.Listener<JSONArray>() {
#Override
public void onResponse(JSONArray response) {
// Parsing json
for (int i = 0; i < response.length(); i++) {
try {
JSONObject JO = response.getJSONObject(i);
GetterSetter getterSetter = new GetterSetter();
getterSetter.setName(JO.getString("name"));
getterSetter.setNumber(JO.getString("number"));
getterSetter.setDate(JO.getString("date"));
myList.add(getterSetter);
} catch (JSONException e) {
e.printStackTrace();
}
}
myAdapter.notifyDataSetChanged();
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
VolleyLog.d(TAG, "Error: " + error.getMessage());
}
}) {
#Override
protected Map<String, String> getParams() {
Map<String, String> params = new HashMap<String, String>();
params.put("myKey", myValue);
return params;
}
};
MySingleton.getInstance().addToRequestQueue(jsonReq);
}
The PHP file is working properly and it is passing json string to android.
The error is happening somewhere within onResponse block. The same block works clean when using StringRequest instead of JsonArrayRequest.
Any idea what exactly is causing this error? Any help or guidance is much appreciated.
* I'm new in Android Volley and the way it works.
EDIT
This is a format/syntax of the url response:
[
{"name":"test",
"number":"123",
"date":"2017-08-22"
},
{"name":"test1",
"number":"1234",
"date":"2017-08-23"
}
]
Try using StringRequest and then create your own JSONArray from the response string:
new JSONArray(response);
You can find example StringRequest from the documentation:
Sending a Simple Request

JSON Parsing Error no value for variable

I am doing a mobile app which retrieves information from my own API. I am trying to get a restaurant details in JSON and parsing them to be displayed. here is the error I am getting:
D/ViewRootImpl: MSG_RESIZED_REPORT: ci=Rect(0, 0 - 0, 0) vi=Rect(0, 0 - 0, 0) or=1
I/Timeline: Timeline: Activity_idle id: android.os.BinderProxy#cf94aa3 time:148477558
E/MainActivity: Response from url: {
"address1": "Market Square, Smithfield, Dublin Dublin 7",
"address2": "Dublin 7",
"cost": 35,
"lat": 53.3489980000,
"lng": -6.2788120000,
"menu_type": "BBQ",
"name": "My Meat Wagon",
"offer": "Meal for 10\u20ac",
"phone": 53463267,
"rate": 4.1
}
E/MainActivity: Json parsing error: No value for restaurants
D/ViewRootImpl: #3 mView = null
and here is the code I am using:
protected Void doInBackground(Void... arg0) {
HttpHandler sh = new HttpHandler();
// Making a request to url and getting response
String jsonStr = sh.makeServiceCall(url);
Log.e(TAG, "Response from url: " + jsonStr);
if (jsonStr != null) {
try {
JSONObject jsonObj = new JSONObject(jsonStr);
// Getting JSON Array node
JSONArray restaurants = jsonObj.getJSONArray("restaurants");
// looping through the JSON object
JSONObject c = restaurants.getJSONObject(0);
String name = c.getString("name");
String address1 = c.getString("address1");
String address2 = c.getString("address2");
String lat = c.getString("lat");
String lng = c.getString("lng");
String cost = c.getString("cost");
String menu_type = c.getString("menu_type");
String rate = c.getString("rate");
String offer = c.getString("offer");
// Phone node is JSON Object
String mobile = c.getString("mobile");
// tmp hash map for single restaurant
HashMap<String, String> restaurant = new HashMap<>();
// adding each child node to HashMap key => value
restaurant.put("name", name);
restaurant.put("address1", address1);
restaurant.put("address2", address2);
restaurant.put("lat", lat);
restaurant.put("lng", lng);
restaurant.put("cost", cost);
restaurant.put("menu_type", menu_type);
restaurant.put("rate", rate);
restaurant.put("offer", offer);
restaurant.put("mobile", mobile);
contactList.add(restaurant);
} catch (final JSONException e) {
Log.e(TAG, "Json parsing error: " + e.getMessage());
runOnUiThread(new Runnable() {
#Override
public void run() {
Toast.makeText(getApplicationContext(),
"Json parsing error: " + e.getMessage(),
Toast.LENGTH_LONG)
.show();
}
});
}
} else {
Log.e(TAG, "Couldn't get json from server.");
runOnUiThread(new Runnable() {
#Override
public void run() {
Toast.makeText(getApplicationContext(),
"Couldn't get json from server. Check LogCat for possible errors!",
Toast.LENGTH_LONG)
.show();
}
});
}
return null;
}
#Override
protected void onPostExecute(Void result) {
super.onPostExecute(result);
// Dismiss the progress dialog
if (pDialog.isShowing())
pDialog.dismiss();
/**
* Updating parsed JSON data into ListView
* */
ListAdapter adapter = new SimpleAdapter(
MainActivity.this, contactList,
R.layout.list_item, new String[]{"name", "address1",
"address2","lat","lng","menu_type","Phone","rate","offer","cost"}, new int[]{R.id.name,
R.id.address1, R.id.address2,R.id.lat,R.id.lng,R.id.menu,R.id.mobile,R.id.rate,R.id.offer,R.id.cost});
lv.setAdapter(adapter);
}
}
}
I would suggest to use Google Gson library for parsing json strings.
Basically you need to import the library, create corresponding POJO and call for gson.fromJson(jsonStringToParseFrom ,YourPOJOClassName.class). So your doInBackground will look like:
protected Void doInBackground(Void... arg0) {
HttpHandler sh = new HttpHandler();
// Making a request to url and getting response
String jsonStr = sh.makeServiceCall(url);
Gson gson = new Gson();
YourPOJOClass parsedResponse = gson.fromJson(jsonStr, YourPOJOClass.class);
If there will be some parsing issues at gson you will get well informed exception of what went wrong and you will get rid off all the boilerplate parsing code.
Many APIs don't return an array when there is only a single result. You'll want to use optJSONArray and if it returns null, check if it's a single result (using another opt method), if it is, skip the array step.
https://docs.oracle.com/middleware/maf230/mobile/api-ref/oracle/adfmf/json/JSONObject.html#optJSONArray-java.lang.String-

Volley JSONArrayRequest - not sending params properly?

I've tried with normal JSONArrayRequests and StringRequests and everything was fine untill now. I want to send an JSONArrayRequest with POST parameters to get some MySQL result in JSON format from the script. Unfortunately I get [] everytime in response. I have checked .php file and query with _GET method and the script worked perfectly returning desired rows in Json format.
I read here (https://stackoverflow.com/a/18052417/4959185) Volley Team have added JSONArrayRequest with _POST parameter to their class. However it does not work in my case. Could you please look what is wrong with that function:
private void getFavouriteRecipes(final String userUniqueId, final int offset) {
JsonArrayRequest favouriteRecipesReq = new JsonArrayRequest(Request.Method.POST,
AppConfig.URL_GETFAVOURITERECIPES, new Response.Listener<JSONArray>() {
#Override
public void onResponse(JSONArray response) {
Log.d("odpowiedz", "Odpowiedź ulubionych: " + response);
for (int i = 0; i < response.length(); i++) {
try {
JSONObject jObj = response.getJSONObject(i);
RecipeItem recipeItem = new RecipeItem();
recipeItem.setRecipeUniqueID(jObj.getString("unique_id"));
recipeItem.setRecipeTitle(jObj.getString("title"));
recipeItem.setRecipeImgThumbnailLink(jObj.getString(
"img_tumbnail_link"));
recipeItem.setRecipeAddAte(jObj.getString("add_date"));
recipeItem.setRecipeKitchenType(jObj.getString("kitchen_type"));
recipeItem.setRecipeMealType(jObj.getString("meal_type"));
recipeItem.setRecipeName(jObj.getString("name"));
recipeItem.setRecipeSurname(jObj.getString("surname"));
recipeItem.setRecipeLikeCount(jObj.getString("like_count"));
recipeFavouriteItems.add(recipeItem);
} catch (JSONException e) {
e.printStackTrace();
showSnackbarInfo("Błąd Json: " + e.getMessage(),
R.color.snackbar_error_msg);
}
}
recipeFavouriteItemsAdapter.notifyDataSetChanged();
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.e("odpowiedz", "Błąd pobierania ulubionych: " +
Integer.toString(error.networkResponse.statusCode));
showSnackbarInfo(Integer.toString(error.networkResponse.statusCode),
R.color.snackbar_error_msg);
}
}) {
#Override
protected Map<String, String> getParams() {
// Posting Parameters to Login URL
Map<String, String> params = new HashMap<>();
params.put("user_unique_id", userUniqueId);
params.put("offset", Integer.toString(offset));
Log.d(TAG, "wysylam parametry: " + userUniqueId + ", " + Integer.toString(offset));
return params;
}
};
// Adding Request to Request Queue
AppController.getInstance().addToRequestQueue(favouriteRecipesReq);
}
My PHP Script:
https://ideone.com/ZxYzHr
I have found another way to get JSONArrayResponse with sending parameters. I think that will help somebody.
U just write standard JSONArrayRequest liek this:
JsonArrayRequest favouriteRecipesReq = new JsonArrayRequest(prepareGetMethodUrl(),
new Response.Listener<JSONArray>() {
#Override
public void onResponse(JSONArray response) {
Log.d("odpowiedz", "Odpowiedź ulubionych: " + response.toString());
for (int i = 0; i < response.length(); i++) {
try {
JSONObject jObj = response.getJSONObject(i);
RecipeItem recipeItem = new RecipeItem();
recipeItem.setRecipeUniqueID(jObj.getString("unique_id"));
recipeItem.setRecipeTitle(jObj.getString("title"));
recipeItem.setRecipeImgThumbnailLink(jObj.getString(
"img_tumbnail_link"));
recipeItem.setRecipeAddAte(jObj.getString("add_date"));
recipeItem.setRecipeKitchenType(jObj.getString("kitchen_type"));
recipeItem.setRecipeMealType(jObj.getString("meal_type"));
recipeItem.setRecipeName(jObj.getString("name"));
recipeItem.setRecipeSurname(jObj.getString("surname"));
recipeItem.setRecipeLikeCount(jObj.getString("like_count"));
recipeFavouriteItems.add(recipeItem);
} catch (JSONException e) {
e.printStackTrace();
}
}
recipeFavouriteItemsAdapter.notifyDataSetChanged();
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.e("odpowiedz", "Błąd pobierania ulubionych: " +
Integer.toString(error.networkResponse.statusCode));
showSnackbarInfo(Integer.toString(error.networkResponse.statusCode),
R.color.snackbar_error_msg);
}
});
// Adding Request to Request Queue
AppController.getInstance().addToRequestQueue(favouriteRecipesReq);
Instead of standard URL to the PHP script I inserted function returning String called prepareGetMethodUrl().
Let's look inside it:
private String prepareGetMethodUrl() {
return AppConfig.URL_GETFAVOURITERECIPES + "?user_unique_id=" + userUniqueId + "&offset=" +
Integer.toString(offset);
}
As you can see it's very simple. I get standard AppConfig.URL_GETFAVOURITERECIPES which is static field in AppConfig class conatining direct link to my PHP script on my serwer f.e http://www.someserversite.com/my_api/gmy_php_script.php and combine it with parametres values I need to send to the script: user_unique_id and it's content userUniqueId and offset which content is offset parsed from int to String.
Inside my script I just call:
<?php
// some code
// Receiving The Post Params
$user_unique_id = $_GET['user_unique_id'];
$offset = $_GET['offset'];
echo $user_unique_id . "<br />";
echo $offset;
?>

Categories

Resources