Im passing a username and a password to url using basic64 auth method. The response is a token. How can i get this token using volley library ?
Thanks in advance
You can pass the JsonRequest by using following code.
JsonObjectRequest req = new JsonObjectRequest(Url, new JSONObject(),
new com.android.volley.Response.Listener<JSONObject>() {
#Override
public void onResponse(JSONObject response) {
try {
Log.v("Response:%n %s", response.toString(0));
JSONObject jsonObject = new JSONObject(response.toString());
String success = jsonObject.getString("success");
// Get your Token Here.
} catch (JSONException e) {
e.printStackTrace();
Toast.makeText(LoginActivity.this, "Server or Connection Error.", Toast.LENGTH_SHORT).show();
builder.dismiss();
}
}
}, new com.android.volley.Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
VolleyLog.e("Error: ", error.getMessage());
}
});
AppController.getInstance().addToRequestQueue(req);
To pass the request in volley you need AppController class.
public class AppController extends Application {
public static final String TAG = AppController.class.getSimpleName();
private RequestQueue mRequestQueue;
private static AppController mInstance;
#Override
public void onCreate() {
super.onCreate();
mInstance = this;
}
public static synchronized AppController getInstance(){
return mInstance;
}
public RequestQueue getRequestQueue(){
if(mRequestQueue == null){
mRequestQueue = Volley.newRequestQueue(getApplicationContext());
}
return mRequestQueue;
}
public <T> void addToRequestQueue(Request<T> req, String tag) {
// set the default tag if tag is empty
req.setTag(TextUtils.isEmpty(tag) ? TAG : tag);
getRequestQueue().add(req);
}
public <T> void addToRequestQueue(Request<T> req) {
req.setTag(TAG);
getRequestQueue().add(req);
}
public void cancelPendingRequests(Object tag) {
if (mRequestQueue != null) {
mRequestQueue.cancelAll(tag);
}
}
}
Related
I want to post user credentials to following url
: http://myurl/authenticate
Parameters : login. Type (JSON)
username : string
password : string
"login":{"username": "JohnDoe","password": "eoDnhoJ" }
If success
{
" r e s u l t " : " S u c c e s s " ,
"response": "Users Session ID"
}
Here is my code
public interface APIService {
#POST("/authenticate")
#FormUrlEncoded
Call<Login> savePost(#Field("username") String username,
#Field("password") String password);
}
public class ApiUtils {
private ApiUtils() {}
public static final String BASE_URL = "http://myurl/";
public static APIService getAPIService() {
return RetrofitClient.getClient(BASE_URL).create(APIService.class);
}
}
public class Login {
#SerializedName("username")
#Expose
private String username;
#SerializedName("password")
#Expose
private String password;
//getters and setters
}
public class RetrofitClient {
private static Retrofit retrofit = null;
public static Retrofit getClient(String baseUrl) {
if (retrofit==null) {
retrofit = new Retrofit.Builder()
.baseUrl(baseUrl)
.addConverterFactory(GsonConverterFactory.create())
.build();
}
return retrofit;
}
}
public class LoginActivity extends AppCompatActivity {
private EditText usernameEditText,passwordEditText;
private Button button;
private APIService mAPIService;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_login);
usernameEditText=(EditText)findViewById(R.id.username);
passwordEditText=(EditText)findViewById(R.id.password);
button=(Button)findViewById(R.id.signup);
mAPIService = ApiUtils.getAPIService();
button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
String uname=usernameEditText.getText().toString();
String pass=passwordEditText.getText().toString();
if(TextUtils.isEmpty(uname)){
Toast.makeText(LoginActivity.this, "Username cannot be empty", Toast.LENGTH_SHORT).show();
return;
}
if(TextUtils.isEmpty(pass)){
Toast.makeText(LoginActivity.this, "Password cannot be empty", Toast.LENGTH_SHORT).show();
return;
}
if(pass.length()<4){
Toast.makeText(LoginActivity.this, "Password should be greater than four characters", Toast.LENGTH_SHORT).show();
return;
}
sendPost(uname, new StringBuilder(uname).reverse().toString());
}
});
}
public void sendPost(String username, String password) {
mAPIService.savePost(username, password).enqueue(new Callback<Login>() {
#Override
public void onResponse(Call<Login> call, Response<Login> response) {
if(response.isSuccessful()) {
showResponse(response.body().toString());
Log.i("Pritish", "post submitted to API." + response.body().toString());
Intent intent=new Intent(getApplicationContext(), MainActivity.class);
startActivity(intent);
finish();
}
}
#Override
public void onFailure(Call<Login> call, Throwable t) {
Log.e("Pritish", "Unable to submit post to API.");
}
});
}
public void showResponse(String response) {
Log.i("Abbu",response);
}
}
Whenever i submit username and password i get null values,can some body please help me?And how can iget the sessionId.I tried looking for various egs but i am so confsued right now.
Instead of follwing code
#POST("/authenticate")
#FormUrlEncoded
Call<Login> savePost(#Field("username") String username,
#Field("password") String password);
Use this code
#POST("/authenticate")
Call<Login> savePost(#Query("username") String username,
#Query("password") String password);
Step 1: instead of this code
public interface APIService {
#POST("/authenticate")
#FormUrlEncoded
Call<Login> savePost(#Field("username") String username,
#Field("password") String password);
}
Use this code:
public interface APIService {
#POST("/authenticate")
Call<Login> savePost(#Body RequestBody body);
}
Step 2: instead of this code in LoginActivity
public void sendPost(String username, String password) {
mAPIService.savePost(username, password).enqueue(new Callback<Login>() {
#Override
public void onResponse(Call<Login> call, Response<Login> response) {
if(response.isSuccessful()) {
showResponse(response.body().toString());
Log.i("Pritish", "post submitted to API." + response.body().toString());
Intent intent=new Intent(getApplicationContext(), MainActivity.class);
startActivity(intent);
finish();
}
}
#Override
public void onFailure(Call<Login> call, Throwable t) {
Log.e("Pritish", "Unable to submit post to API.");
}
});
}
Change to this code :
public void sendPost(String username, String password) {
HashMap<String, String> params = new HashMap<>();
params.put("username", username);
params.put("password", password);
String strRequestBody = new Gson().toJson(params);
//create requestbody
final RequestBody requestBody = RequestBody.create(MediaType.
parse("application/json"),strRequestBody);
mAPIService.savePost(requestBody).enqueue(new Callback<Login>() {
#Override
public void onResponse(Call<Login> call, Response<Login> response) {
if(response.isSuccessful()) {
showResponse(response.body().toString());
Log.i("Pritish", "post submitted to API." + response.body().toString());
Intent intent=new Intent(getApplicationContext(), MainActivity.class);
startActivity(intent);
finish();
}
}
#Override
public void onFailure(Call<Login> call, Throwable t) {
Log.e("Pritish", "Unable to submit post to API.");
}
});
}
Replace your Login class by following
#SerializedName("result")
#Expose
private String rESULT;
#SerializedName("response")
#Expose
private String response;
public String getRESULT() {
return rESULT;
}
public void setRESULT(String rESULT) {
this.rESULT = rESULT;
}
public String getResponse() {
return response;
}
public void setResponse(String response) {
this.response = response;
}
Add ServiceGenerator class :
public class ServiceGenerator {
private static OkHttpClient.Builder httpClient = new OkHttpClient.Builder();
private static Retrofit.Builder builder =
new Retrofit.Builder()
.baseUrl(BASEURL)
.addConverterFactory(ScalarsConverterFactory.create());
public static <S> S createService(Class<S> serviceClass) {
Retrofit retrofit = builder.client(httpClient.build()).build();
return retrofit.create(serviceClass);
}
public static Retrofit getRetrofit()
{
return builder.client(httpClient.build()).build();
}
}
2.Add interface RetrofitAPI :
public interface RetrofitApi {
#POST("/api/v1/user")
Call<ResponseBody> login(#Body RequestBody loginBody);
}
3.Add method for login in your manager class :
public void retrofitLogin(JSONObject login, final String tag) {
RetrofitApi service = ServiceGenerator.createService(RetrofitApi.class);
Call<ResponseBody> result = service.login(convertJsonToRequestBody(login));
result.enqueue(new Callback<ResponseBody>() {
#Override
public void onResponse(Call<ResponseBody> call, retrofit2.Response<ResponseBody> response) {
retrofitCheckResponse(response, tag);
}
#Override
public void onFailure(Call<ResponseBody> call, Throwable t) {
if (t instanceof IOException) {
Log.e("retrofit error", "retrofit error");
sendErrorRetrofit(mContext.getString(R.string.ERROR), 500, tag);
}
}
});
}
Method to convert JSONObject to RequestBody :
private RequestBody convertJsonToRequestBody(JSONObject jsonObject) {
if (jsonObject != null) {
return RequestBody.create(okhttp3.MediaType.parse("application/json; charset=utf-8"), jsonObject.toString());
} else {
return null;
}
}
4.Now call your retrofitLogin method :
JSONObject mLoginParams = new JSONObject();
JSONObject mLoginObj = new JSONObject();
mLoginParams.put("username", uname);
mLoginParams.put("password", pass);
mLoginObj.put("appType","mobile");
mLoginObj.put("user", mLoginParams);
volleyRequest.retrofitLogin(mLoginObj, "Login");
I need to call an api to get a json data using android volly. I have a method implemented inside class A to call the get request as shown
class A{
public static String getList(Context context,String url)
{
final String[] result = new String[1];
JsonArrayRequest req = new JsonArrayRequest(url,
new Response.Listener<JSONArray>() {
#Override
public void onResponse(JSONArray response) {
Log.e("response",response.toString());
result[0] =response.toString();
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.e("responseerror",error.toString());
result[0] =error.toString();
}
});
MySingleton.getInstance(context).addToRequestQueue(req);
return result[0];
}
}
Inside class B i am accesing this method
class B {
String responce= A.getList(activity,url);
}
Here i can pass the context and url to get json data. But the problem is getList() method ruturs result even before it gets any response from the server. The app have more than one class which needs to call get request. If i will use this code snippet inside every such class then it will be against DRY principle. So what is the proper procudure to follow in this scenario?
Use an interface like below.
class A {
private final WeakReference<ResponseListener> responseListenerWeakRef;
public A(ResponseListener responseListener) {
responseListenerWeakRef = new WeakReference<ResponseListener>(responseListener);
}
public String getList(Context context, String url) {
JsonArrayRequest req = new JsonArrayRequest(url,
new Response.Listener<JSONArray>() {
#Override
public void onResponse(JSONArray response) {
Log.e("response",response.toString());
if (responseListener!=null && responseListener.get()!=null) {
responseListener.get().onResponse(response.toString());
}
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.e("responseerror",error.toString());
if (responseListener!=null && responseListener.get()!=null) {
responseListener.get().onResponse(error.toString());
}
}
}
);
MySingleton.getInstance(context).addToRequestQueue(req);
}
public interface ResponseListener {
void onResponse(String response);
}
}
class B implements A.ResponseListener {
private void makeApiCall() {
new A(this).getList(activity, url);
}
#Override
public void onResponse(String response) {
// Do something with the response.
}
}
I'm using getConnection method in my program and I want to restore the response in a variable like "String result " in-order to use in another class, but I don't know how I must change the method. Does anyone have an idea?.
public class Webservice {
public static void getConnection(Context context, String url){
RequestQueue queue = Volley.newRequestQueue(context);
StringRequest stringRequest = new StringRequest(Request.Method.GET, url,
new Response.Listener<String>() {
#Override
public void onResponse(String response) {
Log.i("TEST", "Response is: "+ response);
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.i("TEST","That didn't work!");
}
});
queue.add(stringRequest);
}
}
You can create a variable in Application class and use it throughout your application like this
public class App extends android.app.Application {
private static App instance;
public static String resultResponse;
public static App getInstance() {
return instance;
}
#Override
public void onCreate() {
super.onCreate();
instance = this;
}
}
Then when you get the response save it like this
public class Webservice {
public static void getConnection(Context context, String url){
RequestQueue queue = Volley.newRequestQueue(context);
StringRequest stringRequest = new StringRequest(Request.Method.GET,
url,
new Response.Listener<String>() {
#Override
public void onResponse(String response) {
Log.i("TEST", "Response is: "+ response);
App.getInstance().resultResponse = response;
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.i("TEST","That didn't work!");
}
});
queue.add(stringRequest);
}
}
Add
android:name = ".App"
in Application in your manifest.
Now Use
App.getInstance().resultResponse
where ever you want through out your Application.
You can use interface having return type String in onResponse method and implement this interface in your required class get String response.
I want to update status for a user when a user closes his app directly.
I tried this but this isn't working :
public class ExitService extends IntentService {
private static String TAG = ExitService.class.getSimpleName();
public ExitService() {
super(TAG);
}
#Override
protected void onHandleIntent(Intent intent) {
if (intent != null) {
String callNo = intent.getStringExtra("callNo");
String status = intent.getStringExtra("status");
updateExitStatus(callNo, status);
}
}
public void updateExitStatus(final String callNo,final String status){
StringRequest strReq1= new StringRequest(Request.Method.POST,
Config.UTL_STATUS, new Response.Listener<String>(){
public void onResponse(String response) {
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.e(TAG, "Error: " + error.getMessage());
Toast.makeText(getApplicationContext(),
error.getMessage(), Toast.LENGTH_SHORT).show();
}
}) {
#Override
protected Map<String, String> getParams() {
Map<String, String> params = new HashMap<String, String>();
params.put("callNo", callNo);
params.put("status",status);
Log.e(TAG, "Posting params: " + params.toString());
return params;
}
};
// Adding request to request queue
MyApplication.getInstance().addToRequestQueue(strReq1);
}
}
I have onResume which will update the status to "1"(taking 1 for online and 0 for offline)
The app should work in background too, therefore onStop and onPause ruled out from this equation.
try this it works for me...
public class App_killed extends Service {
#Override
public IBinder onBind(Intent intent) {
return null;
}
#Override
public int onStartCommand(Intent intent, int flags, int startId) {
Log.d("ClearFromRecentService", "Service Started");
return START_NOT_STICKY;
}
#Override
public void onDestroy() {
super.onDestroy();
Log.d("ClearFromRecentService", "Service Destroyed");
}
public void onTaskRemoved(Intent rootIntent) {
Log.e("ClearFromRecentService", "END");
//Code here call your network call using volley/Asynch task..
App_close();
Toast.makeText(getApplicationContext(), "Warning: App killed", Toast.LENGTH_LONG).show();
//stopSelf();
}
private void App_close() {
// Tag used to cancel the request
String tag_string_req = "close_app";
StringRequest strReq = new StringRequest(Request.Method.POST,
AppConfig.URL_CLOSE_APP, new Response.Listener<String>() {
#Override
public void onResponse(String response) {
Log.d("close App", "Killed Response: " + response.toString());
} catch (Exception e) {
// JSON error
e.printStackTrace();
}
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
Log.e("close app", "Killed Error: " + error.getMessage());
}
}) {
#Override
protected Map<String, String> getParams() {
// Posting parameters to login url
Map<String, String> params = new HashMap<String, String>();
params.put("status", status);
params.put("mobile", callNo);
return params;
}
};
// Adding request to request queue
VollyGlobal.getInstance().addToRequestQueue(strReq, tag_string_req);
}
}
IN manifest
<service
android:name=".App_killed"
android:stopWithTask="false" />
Now start the service in your MainActivity;
startService(new Intent(getBaseContext(), App_killed.class));
Now in your VolleyGlobal class:
public class VollyGlobal extends Application {
private static Context context;
public static final String TAG = VollyGlobal.class.getSimpleName();
private RequestQueue mRequestQueue;
private static VollyGlobal mInstance;
#Override
public void onCreate() {
super.onCreate();
mInstance = this;
VollyGlobal.context = getApplicationContext();
}
public static Context getAppContext() {
return VollyGlobal.context;
}
public static synchronized VollyGlobal getInstance() {
return mInstance;
}
public RequestQueue getRequestQueue() {
if (mRequestQueue == null) {
mRequestQueue = Volley.newRequestQueue(getApplicationContext());
}
return mRequestQueue;
}
public <T> void addToRequestQueue(Request<T> req, String tag) {
req.setTag(TextUtils.isEmpty(tag) ? TAG : tag);
getRequestQueue().add(req);
}
public <T> void addToRequestQueue(Request<T> req) {
req.setTag(TAG);
getRequestQueue().add(req);
}
public void cancelPendingRequests(Object tag) {
if (mRequestQueue != null) {
mRequestQueue.cancelAll(tag);
}
}
private Request<?> setDefaultRetryPolicy(Request<?> request) {
request.setRetryPolicy(new DefaultRetryPolicy(0,
DefaultRetryPolicy.DEFAULT_MAX_RETRIES, DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));
return request;
}
}
Make your call to Server in Intent Service & call that service from onDestroy before super.onDestory().
#Override
protected void onDestroy() {
startService(new Intent(this, ServerUpdateIntentService.class));
super.onDestroy();
}
And for Intent Service use this link :
https://code.tutsplus.com/tutorials/android-fundamentals-intentservice-basics--mobile-6183
I am trying to get the number of "replies" or length of a response from the network here is my request below.
public class Replies {
private String questionId;
private VolleySingleton mVolleySingleton;
private RequestQueue mRequestQueue;
public int replies;
private String url;
//Predondition:Place the id of the questions into the constructor
//as well as the url
//Postcondition: counts the number of replies
public Replies(String questionId) {
this.questionId = questionId;
JsonRequestMethod();
}
public void JsonRequestMethod() {
url = "sampleURl"
mVolleySingleton = VolleySingleton.getInstance();
mRequestQueue = mVolleySingleton.getRequestQueue();
JsonArrayRequest request = new JsonArrayRequest(Request.Method.GET,url, (String) null, new Response.Listener<JSONArray>() {
#Override
public void onResponse(JSONArray response) {
replies=response.length();
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
System.out.println(error);
}
});
mRequestQueue.add(request);
}
public String getReplies() {
return replies+"";
}
}
Also, in my adapter i have in my on bindviewholder this line of code
Replies replies=new Replies(currentSearch.getId());
holder.replies.setText(replies.getReplies());
However, it keeps getting set to 0 because its not waiting for the response, and the response is not 0. How do i fix this?
Maybe you can
public class Replies {
...
private NetWorkFinishListener listener;
void setListener(NetWorkFinishListener listener){
this.listener = listener;
}
public interface NetWorkFinishListener{
void onSuccess(int replies);
void onFailed(VolleyError error);
}
JsonArrayRequest request = new JsonArrayRequest(Request.Method.GET,url, (String) null, new Response.Listener<JSONArray>() {
#Override
public void onResponse(JSONArray response) {
replies=response.length();
if(listener != null){
listener.onSuccess(replies);
}
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
System.out.println(error);
if(listener != null){
listener.onFailed(error);
}
}
});
}
And
Replies replies=new Replies(currentSearch.getId());
replies.setListener(new NetWorkFinishListener() {
#Override
public void onSuccess(int replies) {
holder.replies.setText(replies.getReplies());
}
#Override
public void onFailed(VolleyError error) {
// do some thing
}
});
//holder.replies.setText(replies.getReplies());
But there is a bug.
Holder may not be the original.But the listener still run Success().
you can use view.setTag() to judge.