How to pass RAW body to the API using volley android - android

I am trying to POST body with my api of XML type. Please have a look at the body below! I have no clue how to pass xml body with the api
<passwordQuestions>
 <passwordQuestion question="security.question.childhood.nickname" answer="nickname"/>
   <passwordQuestion question="security.question.father.middleName" answer="father.middleName"/>
   <passwordQuestion question="security.question.oldestSibling.middleName" answer="oldestSibling.middleName"/>
</passwordQuestions>
type:
Content-Type text/xml
This is my code need to add body here!
public void setSeqQns(String oldAPIEmail, String token,String appKey, String mLocale, String firstQuestion, String firstAnswer,
String secondQuestion, String secondAnswer, String thirdQuestion, String thirdAnswer,
final Action1<String> onUpdateSetAnswerSuccess, final Action1<String> onUpdateSetAnswerFail) {
if(userId == null){
Log.e(TAG, "userId is null");
Observable<String> observable = Observable.just("userId is null");
observable.subscribe(onUpdateSetAnswerFail);
return;
}
String url = BASE_URL + Util.addUseridToUri(URI_SET_ANSWER, userId);
Response.Listener<String> listener =
new Response.Listener<String>() {
#Override
public void onResponse(String response) {
Log.v(TAG, "Update seq qns response: "+ response);
Observable<String> observable = Observable.just(response);
observable.subscribe(onUpdateSetAnswerSuccess);
}
};
Response.ErrorListener errorListener = new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
String errorCode = null;
if (error.networkResponse != null) {
Map<String, String> headers = error.networkResponse.headers;
if (headers != null) {
errorCode = headers.get(PulseAPIConstants.HEADER_XIcErrorCode);
Log.e(TAG, "received error code: " + errorCode);
}
}
// observes this API request and will call the loginFailure action
Observable<String> observable = Observable.just(errorCode);
observable.subscribe(onUpdateSetAnswerFail);
}
};
AuthenticatedGsonRequest<String> request = new AuthenticatedGsonRequest<>(
Request.Method.POST,
url,
new TypeToken<String>() {}.getType(),
null,
listener,
errorListener,
oldAPIEmail,
token,
appKey,
mLocale);
addToRequestQueue(request, TAG_SET_ANSWER);
}
I need to add xml(RAW body data) to the URI.
Thanks!!

Related

Caused by: java.lang.IllegalStateException: Expected BEGIN_OBJECT but was STRING at line 1 column 1 path $

I need help with my project please. I don't really have a lot to say other than that I'm trying to add payment gateway to my android app using stripe. I followed the documentation here. Towards the end where I have to test everything my app crashes and I get this error message I am almost done with this but this is the only thing in my way. Please help me. Thanks in advance
//My code is here
private void startCheckout() {
// Create a PaymentIntent by calling the sample server's /create-payment-intent endpoint.
MediaType mediaType = MediaType.parse("application/json; charset=utf-8");
String json = "{"
+ "\"currency\":\"usd\","
+ "\"items\":["
+ "{\"id\":\"photo_subscription\"}"
+ "]"
+ "}";
RequestBody body = RequestBody.create(mediaType,json);
Request request = new Request.Builder()
.url(BACKEND_URL + "create-payment-intent")
.post(body)
.build();
httpClient.newCall(request)
.enqueue(new PayCallback(this));
// Hook up the pay button to the card widget and stripe instance
Button payButton = findViewById(R.id.payButton);
payButton.setOnClickListener((View view) -> {
CardInputWidget cardInputWidget = findViewById(R.id.cardInputWidget);
PaymentMethodCreateParams params = cardInputWidget.getPaymentMethodCreateParams();
if (params != null) {
ConfirmPaymentIntentParams confirmParams = ConfirmPaymentIntentParams
.createWithPaymentMethodCreateParams(params, paymentIntentClientSecret);
stripe.confirmPayment(this, confirmParams);
}
});
}
private void displayAlert(#NonNull String title,
#Nullable String message,
boolean restartDemo) {
AlertDialog.Builder builder = new AlertDialog.Builder(this)
.setTitle(title)
.setMessage(message);
if (restartDemo) {
builder.setPositiveButton("Restart demo",
(DialogInterface dialog, int index) -> {
CardInputWidget cardInputWidget = findViewById(R.id.cardInputWidget);
cardInputWidget.clear();
startCheckout();
});
} else {
builder.setPositiveButton("Ok", null);
}
builder.create().show();
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
// Handle the result of stripe.confirmPayment
stripe.onPaymentResult(requestCode, data, new PaymentResultCallback(this));
}
private void onPaymentSuccess(#NonNull final Response response) throws IOException {
Gson gson = new Gson();
Type type = new TypeToken<Map<String, String>>(){}.getType();
Map<String, String> responseMap = gson.fromJson(
Objects.requireNonNull(response.body()).string(),
type
);
// The response from the server includes the Stripe publishable key and
// PaymentIntent details.
// For added security, our sample app gets the publishable key from the server
String stripePublishableKey = responseMap.get("publishableKey");
paymentIntentClientSecret = responseMap.get("clientSecret");
// Configure the SDK with your Stripe publishable key so that it can make requests to the Stripe API
stripe = new Stripe(
getApplicationContext(),
Objects.requireNonNull(stripePublishableKey)
);
}
private static final class PayCallback implements Callback {
#NonNull private final WeakReference<PaymentPageActivity> activityRef;
PayCallback(#NonNull PaymentPageActivity activity) {
activityRef = new WeakReference<>(activity);
}
#Override
public void onFailure(Request request, IOException e) {
final PaymentPageActivity activity = activityRef.get();
if (activity == null) {
return;
}
activity.runOnUiThread(() ->
Toast.makeText(
activity, "Error: " + e.toString(), Toast.LENGTH_LONG
).show()
);
}
#Override
public void onResponse(Response response) throws IOException {
final PaymentPageActivity activity = activityRef.get();
if (activity == null) {
return;
}
if (!response.isSuccessful()) {
activity.runOnUiThread(() ->
Toast.makeText(
activity, "Error: " + response.toString(), Toast.LENGTH_LONG
).show()
);
} else {
activity.onPaymentSuccess(response);
}
}
}
private static final class PaymentResultCallback
implements ApiResultCallback<PaymentIntentResult> {
#NonNull private final WeakReference<PaymentPageActivity> activityRef;
PaymentResultCallback(#NonNull PaymentPageActivity activity) {
activityRef = new WeakReference<>(activity);
}
#Override
public void onSuccess(#NonNull PaymentIntentResult result) {
final PaymentPageActivity activity = activityRef.get();
if (activity == null) {
return;
}
PaymentIntent paymentIntent = result.getIntent();
PaymentIntent.Status status = paymentIntent.getStatus();
if (status == PaymentIntent.Status.Succeeded) {
// Payment completed successfully
Gson gson = new GsonBuilder().setPrettyPrinting().create();
activity.displayAlert(
"Payment completed",
gson.toJson(paymentIntent),
true
);
} else if (status == PaymentIntent.Status.RequiresPaymentMethod) {
// Payment failed – allow retrying using a different payment method
activity.displayAlert(
"Payment failed",
Objects.requireNonNull(paymentIntent.getLastPaymentError()).getMessage(),
false
);
}
}
#Override
public void onError(#NonNull Exception e) {
final PaymentPageActivity activity = activityRef.get();
if (activity == null) {
return;
}
// Payment request failed – allow retrying using the same payment method
activity.displayAlert("Error", e.toString(), false);
}
}
int this line
Map<String, String> responseMap = gson.fromJson(
Objects.requireNonNull(response.body()).string(),
type
);
you shold pass a json Object not a String, use GSON to fix it
something like that :
Gson g = new Gson();
Foo f = g.fromJson(jsonString, bar.class)

Android App , how to communicate between Activity, Service and SyncAdapter

Hi Im working on an android app which works both online and offline. So if its connected to wifi , when i click on save button in the Activity , there are multiple requests (StringRequest) sent to server to update the db. And if offline it saves the data to sqlite and once wifi is available, it automatically syncs the data using SyncAdapter. My problem is there is lot of redundant/duplicate code - one for Activity and one for SyncAdapter and i'm trying to cleanup the code. The only difference between the both for each StringRequests in Activity , Response.Listener & Response.ErrorListener shows some alerts in the Activity and in SyncAdapter it just logs the messages.
Now i have written a Service class that can be used by both activity and syncadapter , the question i have is how can i send alerts/updates to activity in the Response.Listener & Response.ErrorListener , without breaking the flow of service methods.
private void Method1 () {
if (NetworkConnection.isNetworkAvailable (this))
{
StringRequest strRequest = new StringRequest (Request.Method.POST, AppConfigURL.API_URL,
new Response.Listener<String> () {
#Override
public void onResponse (String response) {
if (response != null) {
Utils.showLog (Log.INFO, AppConfigTags.SERVER_RESPONSE, response, true);
} else {
Utils.showOkDialog (MainActivity.this, "Custom alert message", false);
}
Method2();
}
},
new Response.ErrorListener () {
#Override
public void onErrorResponse (VolleyError error) {
Utils.showLog (Log.ERROR, AppConfigTags.VOLLEY_ERROR, error.toString (), true);
Method2();
}
}) {
#Override
public byte[] getBody () throws com.android.volley.AuthFailureError {
JSONObject sendJSON = db.getOfflineSavedOrderDetails();
String str = "{\"API_username\":\"" + Constants.api_username + "\",\n" +
"\"API_password\":\"" + Constants.api_password + "\",\n" +
"\"API_function\":\"updateSavedFixedDetails\",\n" +
"\"API_parameters\": " + String.valueOf(sendJSON) + "}";
Utils.showLog (Log.INFO, AppConfigTags.PARAMETERS_SENT_TO_THE_SERVER, str, true);
return str.getBytes ();
}
public String getBodyContentType () {
return "application/json; charset=utf-8";
}
};
AppController.getInstance().addToRequestQueue(strRequest);
} else {
Method2();
}
}
private void Method2 () {
if (NetworkConnection.isNetworkAvailable (this))
{
StringRequest strRequest = new StringRequest (Request.Method.POST, AppConfigURL.API_URL,
new Response.Listener<String> () {
#Override
public void onResponse (String response) {
if (response != null) {
Utils.showLog (Log.INFO, AppConfigTags.SERVER_RESPONSE, response, true);
} else {
Utils.showLog (Log.WARN, AppConfigTags.SERVER_RESPONSE, AppConfigTags.DIDNT_RECEIVE_ANY_DATA_FROM_SERVER, true);
}
Method3();
}
},
new Response.ErrorListener () {
#Override
public void onErrorResponse (VolleyError error) {
Utils.showOkDialog (MainActivity.this, "Connection Error: My custom error", false);
Method3();
}
}) {
#Override
public byte[] getBody () throws com.android.volley.AuthFailureError {
JSONObject sendJSON = db.getOfflineSavedOrderDetails();
String str = "{\"API_username\":\"" + Constants.api_username + "\",\n" +
"\"API_password\":\"" + Constants.api_password + "\",\n" +
"\"API_function\":\"updateContractDetails\",\n" +
"\"API_parameters\": " + String.valueOf(sendJSON) + "}";
Utils.showLog (Log.INFO, AppConfigTags.PARAMETERS_SENT_TO_THE_SERVER, str, true);
return str.getBytes ();
}
public String getBodyContentType () {
return "application/json; charset=utf-8";
}
};
AppController.getInstance().addToRequestQueue(strRequest);
} else {
Method3();
}
}

Android Volley Request Identity onErrorResponse Section

public void getTestDats(String unique_id) {
final String tag = "testList";
String url = Constants.BASE_URL + "test_module.php";
Map<String, String> params = new HashMap<String, String>();
params.put("user_id", SharedPreferenceUtil.getString(Constants.PrefKeys.PREF_USER_ID, "1"));
params.put("unique_id", unique_id);//1,2,3,4,5
DataRequest loginRequest = new DataRequest(Method.POST, url, params, new Response.Listener<JSONObject>() {
#Override
public void onResponse(JSONObject response) {
switch (response.optInt("unique_id")) {
case 1:
//task 1
break;
case 2:
//task 2
break;
default:
//nothing
}
}
}, new ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
//I want to know which unique_id request is failed
}
});
loginRequest.setRetryPolicy(new DefaultRetryPolicy(20000, 0, DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));
AppController.getInstance().addToRequestQueue(loginRequest, tag);
}
I'm trying to identity which request is failed with having unique_id.
I'm calling getTestDats("1") function with unique_id. And function called 10 times and all the api call in addToRequestQueue.
When API go into Success part its working as per code.
But when API go into Error part I didn't identity the request.
Is there any way to know my request param so I can retry with particular unique_id request.
set a field in loginRequest and in onErrorResponse access the field like loginRequest.getUniqueId()
Alternatively, create a seperate class that implements Response.Listener and ErrorListener
Response Listener class:
public class MyReponseListener implements Response.Listener<JSONOBject>{
private long uniqId;
public MyResponseListener(long uniqId){
this.uniqId = uniqId;
}
#Override
public void onResponse(JSONObject response) {
System.out.println("response for uniqId " + uniqId);
// do your other chit chat
}
}
ErrorListener class:
public class MyErrorListener implements ErrorListener{
private long uniqId;
public MyErrorListener(long uniqId){
this.uniqId = uniqId;
}
#Override
public void onErrorResponse(VolleyError error) {
System.out.println("Error for uniqId : " + uniqId);
}
}
Now call it like:
DataRequest loginRequest = new DataRequest(Method.POST, url, params, new MyResponeListener(uniqId), new MyErrorListener(uniqId));
Now if you want some code of the calling class to be accessible in the ErrorListener class then do the following:
1. In calling class put the codes you want to access in methods
2. Create an interface with those method
3. The calling class will implement that interface
4. Pass the interface to constructor of the MyErrorListener or MyResponseListener
for example an activity calls the volley request, on error you want to show a message.
put that show error codes in a method:
public void showMessage(int errorCode){
//message according to code
}
now create an interface
public interface errorMessageInterface{
void showMessage(int errorCode);
}
the activity will implement errorMessageInterface and pass this to the constructor of MyErrorListener and save it in a field.
Inside onErrorResponse, you will call
field.showMessage()
You can parse error response in the same way as you parse success response. I use similar solution in my projects.
public class VolleyErrorParser {
private VolleyError mError;
private String mBody;
private int mUniqueId = -1;
public VolleyErrorParser(VolleyError e){
mError = e;
parseAnswer();
parseBody();
}
private void parseBody() {
if (mBody==null)
return;
try{
JSONObject response = new JSONObject(mBody);
mUniqueId = response.getOptInt("unique_id");
}catch (JSONException e){
e.printStackTrace();
}
}
private void parseAnswer() {
if (mError!=null&&mError.networkResponse!=null&&mError.networkResponse.data!=null){
mBody = new String(mError.networkResponse.data);
}
}
public String getBody(){
return mBody;
}
public int getUniqueId(){
return mUniqueId;
}
}
Use:
...
, new ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
int id = new VolleyErrorParse(error).getUniqueId();
switch (id) {
case -1:
//unique id not found in the answer
break;
case 1:
//task 1
break;
case 2:
//task 2
break;
default:
//nothing
}
}
}
...
Just add this code to identify which type of error you are facing.Add this in your onError() method :
if (error instanceof TimeoutError) {
Log.e(TAG, "TimeoutError");
} else if (error instanceof NoConnectionError) {
Log.e(TAG,"tNoConnectionError");
} else if (error instanceof AuthFailureError) {
Log.e(TAG,"AuthFailureError");
} else if (error instanceof ServerError) {
Log.e(TAG,"ServerError");
} else if (error instanceof NetworkError) {
Log.e(TAG,"NetworkError");
} else if (error instanceof ParseError) {
Log.e(TAG,"ParseError");
}
Log the unique_id before making a request i.e; after params.put("unique_id", unique_id);//1,2,3,4,5. And also once you get the response in onResponse() method. And cross verify what exactly is happening.
most of the solutions here will "work" but they are too complex .. for me :)
here is the simplest option with least code change I can think of:
...
final Map<String, String> params = new HashMap<String, String>();
params.put("user_id", SharedPreferenceUtil.getString(Constants.PrefKeys.PREF_USER_ID, "1"));
params.put("unique_id", unique_id);//1,2,3,4,5
DataRequest loginRequest = new DataRequest(Method.POST, url, params, new Response.Listener<JSONObject>() {
#Override
public void onResponse(JSONObject response) {
switch (params.get("unique_id")) {
case 1:
//task 1
break;
case 2:
//task 2
break;
default:
//nothing
}
}
...
All the above answers seem to be correct.But i recommend you to do this in an optimized way. If you will add error handling code in all onErrorResponse() then it will create duplication. So create a seperate method in Utils or some other class and just call that method by passing error object to the method. Also you can inflate some dialog or toast to display an error message.
public static void handleError(final Context context, String alertTitle,
Exception exception, String logTag) {
if (context != null) {
if (exception instanceof TimeoutError)
message = context.getString(R.string.TimeoutError);
else if (exception instanceof NoConnectionError)
message = context.getString(R.string.NoConnectionError);
else if (exception instanceof AuthFailureError)
message = context.getString(R.string.AuthFailureError);
else if (exception instanceof ServerError)
message = context.getString(R.string.ServerError);
else if (exception instanceof NetworkError)
message = context.getString(R.string.NetworkError);
else if (exception instanceof ParseError)
message = context.getString(R.string.ParseError);
message = exception.getMessage();
DialogHelper.showCustomAlertDialog(context, null,
alertTitle, message, "ok",
new OnClickListener() {
#Override
public void onClick(DialogInterface dialog,
int which) {
}
}, null, null);
}
}
I think you have to make one conman method on Base class. As given bellow which I used in my code for calling php web api
/**
* <h1> Use for calling volley webService </h1>
*
* #param cContext Context of activity from where you call the webService
* #param mMethodType Should be POST or GET
* #param mMethodname Name of the method you want to call
* #param URL Url of your webService
* #param mMap Key Values pairs
* #param initialTimeoutMs Timeout of webService in milliseconds
* #param shouldCache Web Api response are stored in catch(true) or not(false)
* #param maxNumRetries maximum number in integer for retries to execute webService
* #param isCancelable set true if you set cancel progressDialog by user event
* #param aActivity pass your activity object
*/
public void callVolley(final Context cContext, String mMethodType, final String mMethodname, String URL,
final HashMap<String, String> mMap, int initialTimeoutMs, boolean shouldCache, int maxNumRetries,
Boolean isProgressDailogEnable, Boolean isCancelable, final Activity aActivity) {
mMap.put("version_key_android",BuildConfig.VERSION_NAME+"");
if (!isOnline(cContext)) {
//showErrorDailog(aActivity, Constant.PleaseCheckInternetConnection, R.drawable.icon);
} else {
StringRequest jsObjRequest;
int reqType = 0;
String RequestURL = URL.trim();
queue = Volley.newRequestQueue(cContext);
if (isProgressDailogEnable) {
customLoaderDialog = new CustomLoaderDialog(cContext);
customLoaderDialog.show(isCancelable);
customLoaderDialog.dialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
#Override
public void onCancel(DialogInterface dialog) {
// finish();
}
});
}
if (mMethodType.trim().equalsIgnoreCase("GET"))
reqType = com.android.volley.Request.Method.GET;
else if (mMethodType.trim().equalsIgnoreCase("POST"))
reqType = com.android.volley.Request.Method.POST;
if (RequestURL.equals(""))
RequestURL = Constant.BASE_URL;
else
RequestURL = URL;
if (Constant.d) Log.d("reqType", reqType + "");
jsObjRequest = new StringRequest(reqType, RequestURL, new com.android.volley.Response.Listener<String>() {
#Override
public void onResponse(String response) {
if (Constant.d) Log.d("response==>" + mMethodname, "" + response);
if (customLoaderDialog != null) {
try {
customLoaderDialog.hide();
} catch (Exception e) {
e.printStackTrace();
}
}
if (response == null || response.length() == 0) {
IVolleyRespose iVolleyRespose = (IVolleyRespose) aActivity;
iVolleyRespose.onVolleyResponse(404, response, mMethodname);
} else {
JSONObject json_str;
try {
json_str = new JSONObject(response);
int status = json_str.getInt("status");
if (status == 100) {
AlertDialog alertDialog = new AlertDialog.Builder(aActivity).create();
alertDialog.setTitle(getResources().getString(R.string.app_name));
alertDialog.setMessage(json_str.getString("message") + "");
alertDialog.setCancelable(false);
alertDialog.setButton(AlertDialog.BUTTON_NEUTRAL, "OK",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
try {
Intent viewIntent =
new Intent("android.intent.action.VIEW",
Uri.parse(Constant.playStoreUrl));
startActivity(viewIntent);
}catch(Exception e) {
Toast.makeText(getApplicationContext(),"Unable to Connect Try Again...",
Toast.LENGTH_LONG).show();
e.printStackTrace();
}
dialog.dismiss();
// return;
}
});
alertDialog.show();
} else {
IVolleyRespose iVolleyRespose = (IVolleyRespose) aActivity;
iVolleyRespose.onVolleyResponse(RESPONSE_OK, response, mMethodname);
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
}, new com.android.volley.Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError arg0) {
// TODO Auto-generated method stub
IVolleyRespose iVolleyError = (IVolleyRespose) aActivity;
iVolleyError.onVolleyError(404, "Error", mMethodname);
if (customLoaderDialog != null) {
customLoaderDialog.hide();
}
}
}) {
#Override
protected Map<String, String> getParams() {
String strRequest = "";
try {
strRequest = getWebservicejsObjRequestforvolley(mMethodname, mMap);
if (Constant.d) Log.d("Request==>", strRequest + "");
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
Map<String, String> params = new HashMap<>();
params.put("json", strRequest);
return params;
}
#Override
public Map<String, String> getHeaders() throws AuthFailureError {
Map<String, String> params = new HashMap<>();
params.put("Content-Type", "application/x-www-form-urlencoded");
return params;
}
};
//if(Constant.d) Log.d("Request==>", jsObjRequest+"");
jsObjRequest.setTag(mMethodname);
jsObjRequest.setShouldCache(shouldCache);
jsObjRequest.setRetryPolicy(new DefaultRetryPolicy(initialTimeoutMs, maxNumRetries, DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));
queue.add(jsObjRequest);
}
}
Please observe that here we make one interface for getting response and error.
Using Interface you can get method name on both response and error so you can identify which web api is successfully called and which give error. You should extend base class to Activity and also implement Interface which you made for getting volley response. Here in above code I show how to bind interface to activity. when you call api by passing activity context.

How to put volley coding in main acitivity.java

This Android app is using Android Studio. The function is to scan and display data from the beacon/eddystone. The app already functions and after the scanning stops, the data saves to the local file. I need to transfer the data to the server. How can i insert the volley coding to the mainacitivity.java. I tried to put under the stopscanning button, but it shows error. Im really beginners to learn about android studio.
Here is the coding:
private void stopScanning(Button scanButton) {
try {
beaconManager.stopRangingBeaconsInRegion(region);
} catch (RemoteException e) {
// TODO - OK, what now then?
}
String scanData = logString.toString();
if (scanData.length() > 0)
{
public class MainActivity extends AppCompatActivity {
//The values of these variables will be fetched by the file(Where you will store data)
private String PREFERENCE_SCANINTERVAL = "scanInterval";
private String PREFERENCE_TIMESTAMP = "timestamp";
private String PREFERENCE_POWER = "power";
private String PREFERENCE_PROXIMITY = "proximity";
private String PREFERENCE_RSSI = "rssi";
private String PREFERENCE_MAJORMINOR = "majorMinor";
private String PREFERENCE_UUID = "uuid";
private String PREFERENCE_INDEX = "index";
private String PREFERENCE_LOCATION = "location";
private String PREFERENCE_REALTIME = "realTimeLog";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
String url = "http://beaconscanner.byethost33.com/beaconscanner.php";//This is the url of your server where you will be sending the data to.
//StringRequest is a class in the Volley Library.
//The constructor of this class has four parameters.
// 1 parameter is Request.Method.POST =this specifies the method type, That is post.
//2 parameter is the url you will be sending the request to.That is the server
//3 parameter is the response listener , It will listen for any response from your server . you will be able to fetch the response from the server using this.
//4 parameter is the error listener, it will listen for any error's during the connection or etc.
StringRequest request = new StringRequest(Request.Method.POST, url, new Response.Listener<String>() {
#Override
public void onResponse(String response) {
//Here you will be able to fetch the response coming from the server.
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
}
})
//This is the method we override.
{
//This is method is used to send the data to the server for post methods. This method returns all the data you want to send to server. This is how you send data using Volley.
#Override
protected Map<String, String> getParams() throws AuthFailureError {
Map<String,String> params = new HashMap<String, String>();
params.put("scanInterval",PREFERENCE_SCANINTERVAL);
params.put("timestamp",PREFERENCE_SCANINTERVAL);
params.put("power",PREFERENCE_POWER);
params.put("proximity",PREFERENCE_PROXIMITY);
params.put("rssi",PREFERENCE_RSSI);
params.put("majorMinor",PREFERENCE_MAJORMINOR);
params.put("uuid",PREFERENCE_UUID);
params.put("index",PREFERENCE_INDEX);
params.put("location",PREFERENCE_LOCATION);
params.put("realTimelog",PREFERENCE_REALTIME);
return params;
}
};//The constructor ends here.
Volley.newRequestQueue(this).add(request);// This is the main potion of this code. if you dont add this you will not be able to send the request to your server. this helps you to send it.
}
}
// Write file
fileHelper.createFile(scanData);
// Display file created message.
Toast.makeText(getBaseContext(),
"File saved to:" + getFilesDir().getAbsolutePath(),
Toast.LENGTH_SHORT).show();
scanButton.setText(MODE_STOPPED);
} else {
// We didn't get any data, so there's no point writing an empty file.
Toast.makeText(getBaseContext(),
"No data captured during scan, output file will not be created.",
Toast.LENGTH_SHORT).show();
scanButton.setText(MODE_STOPPED);
}
}
Please add your stacktrace. Also I guess that you want to send the data using the body not the params :). In that case, call the request using the following signature:
new JsonObjectRequest(Request.Method.POST, url, new JSONObject(bodyData), new Response.Listener<JSONObject>() { }
public void sendMyData(HashMap map) {
String url = "http://"....";
StringRequest request = new StringRequest(Request.Method.POST, url, new Response.Listener<String>() {
#Override
public void onResponse(String response) {
progressBar.setVisibility(View.INVISIBLE);
try {// to receive server response, in this example it's jsonArray
JSONArray jsonArray = new JSONArray(response);
//code
}
} catch (JSONException e) {
e.printStackTrace();
}
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
System.out.println(error);
}
}) {
#Override
public String getBodyContentType() { // if your server uses java restfull webservice , you have to override this content type
return "application/json";
}
#Override
protected Map<String, String> getParams() throws AuthFailureError {// parameters which should server receive
Map<String, String> parameters =map;
return parameters;
}
};
requestQueue.add(request);
}

Android: how return a value from JsonObjectRequest?

Let's say I have this Dashboard.java:
public class DashboardActivity extends ActionBarActivity {
private TextView login_response;
private static String TAG = DashboardActivity.class.getSimpleName();
final static String API_URL_ACCOUNT = "http://www.example.com/apiv2/account";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_dashboard);
login_response = (TextView) findViewById(R.id.login_response);
Intent intent = getIntent();
if(intent.hasExtra("TOKEN"))
{
String token = intent.getStringExtra("TOKEN");
getShopName(token);
}
else
{
}
And this is the getShopName method:
private void getShopName(String token) {
JsonObjectRequest req = new JsonObjectRequest(API_URL_ACCOUNT + "?token=" + token, null,
new Response.Listener<JSONObject>() {
#Override
public void onResponse(JSONObject response) {
try {
VolleyLog.v("Response:%n %s", response.toString(4));
JSONArray account = response.getJSONArray("account");
//Log.d(TAG, "Account: "+account.toString());
JSONObject shop = account.getJSONObject(0);
String name_shop = shop.getString("name_shop");
} catch (JSONException e) {
e.printStackTrace();
}
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
VolleyLog.e("Error: ", error.getMessage());
}
});
// add the request object to the queue to be executed
VolleyController.getInstance().addToRequestQueue(req);
}
My goal is to have
if(intent.hasExtra("TOKEN"))
{
String token = intent.getStringExtra("TOKEN");
String shop_name = getShopName(token);
}
The "shop_name" in variable, to reuse in other part.
So, I know that void doesn't return nothing, but, I tried to edit like this answer, without success:
How can I return value from function onResponse of Volley?
Thank you
The issue is not returning a value from a JsonObjectRequest, but rather that you're trying to do an asynchronous operation in a synchronous way.
Here is a great explanation: Asynchronous vs synchronous execution, what does it really mean?
And to your specific question: I advise using an AsyncTask for your network operation.

Categories

Resources