I am using Retrofit To Pass HashMap to Laravel Restful API. I need help to catch this hashmap and convert it to an associative array so I can loop through and insert into MySql database. Please see the code below.
Android
#FormUrlEncoded
#POST("create_phone_contacts")
Call<ResponseBody> createPhoneContacts(
#Field("id") String id,
#FieldMap Map<String, String> phoneContactPhones,
#FieldMap Map<String, String> phoneContactEmails
);
Laravel
class CreatePhoneContactsController extends Controller
{
public function create(Request $request)
{
$phoneContactsPhones = new PhoneContactsPhonesModel;
$phoneContactsPhones->mysql_user_id = $request->id;
$phoneContactsPhones->phone = $request->phone;
$phoneContactsPhones->name = $request->name;
$phoneContactsPhones->save();
$phoneContactsEmails = new PhoneContactsEmailsModel;
$phoneContactsEmails->mysql_user_id = $request->id;
$phoneContactsEmails->email = $request->email;
$phoneContactsEmails->name = $request->name;
$phoneContactsEmails->save();
if ($phoneContactsPhones->save() && $phoneContactsEmails->save()) {
return ['success' => 'Phone Contacts Created'];
} else {
return ['failure' => 'Phone Contacts Failure'];
}
}
}
Here I am just catching the fields, how should I catch the hashmap in Laravel and convert it into associative array... thanks....
This is working now, it will take the map send it via retrofit and insert into mysql.
Activity
Call<JsonObject> call = RetrofitMySql
.getInstance()
.getApi()
.createPhoneContacts(mySqlUserId,
namePhoneMap);
call.enqueue(new Callback<JsonObject>() {
#Override
public void onResponse(Call<JsonObject> call,
Response<JsonObject> response) {
JSONObject jsonObject = null;
try {
jsonObject = new JSONObject(new Gson().toJson(response.body()));
Log.d("",
"JsonReturned: " + jsonObject);
} catch (JSONException e) {
e.printStackTrace();
}
}
#Override
public void onFailure(Call<JsonObject> call,
Throwable t) {
Log.d("response",
"Getting response from server : " + t);
}
});
API
#POST("create_phone_contacts/{id}")
Call<JsonObject> createPhoneContacts(
#Path("id") String id,
#Body Map<String, String> namePhoneMap
);
Laravel
public function create(Request $request, $id)
{
$json = json_decode($request->getContent(), true);
foreach ($json as $key => $value) {
$users = new PhoneContactsPhonesModel;// ---> here
$users->mysql_user_id = $id;
$users->phone = $key;
$users->name = $value;
$users->save();
}
}
Related
I am trying to use login api via retrofit. I need to send only mobile number. When i am using postman body it is getting an output. but when iam calling with android its getting an error json like below
{
"error": "Validation error",
"error_code": "001",
"Validation_errors": {
"mobile": "<p>The Mobile field is required.</p>"
}
}
HomeActivity.class
ApiInterface apiService =
ApiClient.getClient().create(ApiInterface.class);
Map<String,String> user = new HashMap<>();
user.put("mobile",username.getText().toString().trim());
Call<ResponseBody> mService = apiService.loginwithno(user);
Log.d("TAG", "response: " + mService.toString());
mService.enqueue(new Callback<ResponseBody>() {
#Override
public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
if (response.isSuccessful()) {
try {
String result = response.body().string();
JSONObject mJsonObject = new JSONObject(result);
Log.d("TAG", "response: " + mJsonObject.toString());
} catch (JSONException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
} else {
buttonVisible();
username.setError("Please try again");
}
}
#Override
public void onFailure(Call<ResponseBody> call, Throwable t) {
call.cancel();
buttonVisible();
Snackbar snackbar = Snackbar.make(buttonLogin,
"Please check your internet connection", Snackbar.LENGTH_LONG);
snackbar.show();
}
ApiClient
public class ApiClient {
public static final String BASE_URL = "http://nast.in/driverpool/api/index.php/";
private static Retrofit retrofit = null;
public static Retrofit getClient() {
retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.build();
return retrofit;
}
}
ApiInterface
public interface ApiInterface {
#POST("account/login?")
Call<ResponseBody> loginwithno(#Body Map<String, String> mobile);
#POST("account/verifyotp")
Call<ResponseBody> verifyotp(#Body HashMap<String, String> mobile);//Param name: mobile, otp
#POST("account/resendotp")
Call<ResponseBody> resentotp(#Body HashMap<String, String> mobile);
}
Postman screenshot
First you don't need '?' in your api and i think you must send json in your #body so create class like this
public class SendLoginData{
#SerializedName("mobile")
public String mobile;
public SendLoginData(String mobile) {
this.mobile = mobile;
}
}
And use it in ApiInterface
#POST("account/login")
Call<ResponseBody> loginwithno(#Body SendLoginData post);
You need to make few changes in code.
Change your login api to receive json like this, include gson library if you have not added in project.
#POST("account/login?")
Call loginwithno(#Body Map mobile);
Create an ApiErrorResponse object to handle your api error. Add getter, setter and #SerializedName as required.
class ApiErrorResponse{
String error;
String error_code;
ValidationErrors Validation_errors;
}
class ValidationErrors{
String mobile;
}
on API error handle like this
if(!response.isSuccessful()){
Converter converter =
ApiClient.getClient().responseBodyConverter(ApiErrorResponse.class, new Annotation[0]);
ApiErrorResponse errors = null;
try {
errors = converter.convert(response.errorBody());
} catch (Exception e) {
}
if(errors!=null){
//Handle your API Error logic here
}
}
I want to display the data in my recyclerview that come from a json data, but Im getting null pointer exception , I dont know where did I do wrong from it.
this is my json data:
{
"value": 1,
"review_profile_results": [
{
"review_id": "1",
"review_name": "Sample",
"review_user_id": "2",
"review_comments": "+ Reputation, trusted",
"review_rate": "4",
"review_rate_def": "Trusted",
"review_date": "2018-07-22 06:17:31"
}
]
}
This is for API interface:
#GET (UrlFinal.pathServiceUrl+"show_profile_reviews.php")
Call <Value> show_profileReviews (#Query("id")String id);
possible URL result that I want to pass
/show_profile_reviews.php?id=c4ca4238a0b923820dcc509a6f75849b
This is for how I passing the data
private void showProfileReviews(){
String userId = MainActivity.user.getId();
String id_md5 = md5(userId);
Toast.makeText(getActivity(), id_md5, Toast.LENGTH_SHORT).show();
Retrofit retrofit = new Retrofit.Builder ()
.baseUrl (UrlFinal.ipUrl)
.addConverterFactory (GsonConverterFactory.create ())
.build ();
ServiceAPI api = retrofit.create (ServiceAPI.class);
Call<Value> call = api.show_profileReviews(id_md5);
call.enqueue(new Callback<Value>() {
#Override
public void onResponse(#NonNull Call<Value> call, #NonNull Response<Value> response) {
if (Objects.requireNonNull(response.body()).getValue() == 1) {
profile_list = Objects.requireNonNull(response.body()).getReviewProfileResults();
adapter = new Adapter_ProfileReviews(getActivity(), profile_list);
recyclerView.setAdapter(adapter);
Log.d("Result", profile_list.toString());
Log.d("Result", call.toString());
}
}
#Override
public void onFailure(#NonNull Call<Value> call, #NonNull Throwable t) {
Log.d("Result", t.getMessage());
}
});
}
public String md5(String s) {
try {
// Create MD5 Hash
MessageDigest digest = java.security.MessageDigest.getInstance("MD5");
digest.update(s.getBytes());
byte messageDigest[] = digest.digest();
// Create Hex String
StringBuilder hexString = new StringBuilder();
for (byte aMessageDigest : messageDigest)
hexString.append(Integer.toHexString(0xFF & aMessageDigest));
return hexString.toString();
}catch (NoSuchAlgorithmException e) {
e.printStackTrace();
}
return "";
}
You have a base url for your retrofit client, so define your interface as follows,
public interface YourApiInterface {
#GET ("/show_profile_reviews")
Call <Value> show_profileReviews (#Query("id")String id);
}
Retrofit call will then be, BASE_URL/show_profile_reviews?id=your_id
If you want to use a dynamic URL then define your interface as follows,
public interface YourApiInterface {
#GET
Call <Value> show_profileReviews (#Url String url);
}
If you use dynamic url then you can pass the Url as,
apiInterface.show_profileReviews("https://base_url/show_profile_reviews.php?id=c4ca4238a0b923820dcc509a6f75849b");
For more,
http://square.github.io/retrofit/
Currently, I am using Retrofit to get data from api. But the format of data is a bit different from other format such as :
["tayl",["taylor swift","taylor swift kanye west","taylor swift famous","taylor swift mp3","taylor lautner","taylor swift wiki","taylor swift 1989","taylor hill","taylor swift 2016","taylor kinney"]]
So, I want to ask for the best solution to parse values to get a list as below if I want to use retrofit:
"taylor swift","taylor swift kanye west","taylor swift famous","taylor swift mp3","taylor lautner","taylor swift wiki","taylor swift 1989","taylor hill","taylor swift 2016","taylor kinney"
The content of the file above is the data which GoogleAutoComplete Api returned for me with the link below :
http://suggestqueries.google.com/complete/search?client=firefox&q=tayl
I implemented the code as below but it is not good:
#Headers({
"Accept: application/json",
"Content-Type: application/json; charset=UTF-8"
})
#GET("complete/search?")
Call<ResponseBody> getAutoComplete(#Query(#Query("q")String query);
The below is response code which I am using:
autoCompleteCall = googleApi.getAutoComplete(client, keyword);
autoCompleteCall.enqueue(new Callback<ResponseBody>() {
#Override
public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
if (response != null &&
response.body() != null) {
System.out.println(" String response======= " + response.body().toString());
return;
}
}
#Override
public void onFailure(Call<ResponseBody> call, Throwable t) {
}
});
But the responsebody returned for me is null.
Please help me in this case.
Thanks.
Define the API endpoint in an interface as follows:
#GET("complete/search")
Call<ResponseBody> getAutoComplete(
#Query("client") String client,
#Query("q") String query);
Make the network request as follows:
Call<ResponseBody> call = service.getAutoComplete("firefox", "tayl");
call.enqueue(new Callback<ResponseBody>() {
#Override
public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
if (response.isSuccessful()) {
ResponseBody body = response.body();
try {
// autocompleteOptions => ["tayl",["taylor swift","taylor lautner",...
String autocompleteOptions = body.string();
JSONArray jsonArray = new JSONArray(autocompleteOptions).getJSONArray(1);
// list => "taylor swift","taylor lautner",...
ArrayList<String> list = GetAutocompleteOptions(jsonArray);
} catch (IOException e) {
e.printStackTrace();
} catch (JSONException e) {
e.printStackTrace();
}
}
}
#Override
public void onFailure(Call<ResponseBody> call, Throwable t) {
}
});
private ArrayList<String> GetAutocompleteOptions(JSONArray jsonArray) throws JSONException {
ArrayList<String> list = new ArrayList<>();
if (jsonArray != null) {
for (int i = 0; i < jsonArray.length(); i++) {
list.add(jsonArray.get(i).toString());
}
}
return list;
}
i wanted to post the json object using retrofit.
i have created following interface:
public interface syncinter {
#POST("url")
void sync_data(#Body JSONObject ordObj, Callback<JsonObject> callback);
}
the following data i want it to post.
final JSONObject ordJsonObj = new JSONObject();
JSONArray ordJsonArray = new JSONArray();
try {
ordJsonObj.put("Order_Nos",mOrdArr.size());
for (int i=0; i<mOrdArr.size();i++) {
JSONObject ordObj = new JSONObject();
ordObj.put("Order_No",mOrdArr.get(i).getorderID());
ordObj.put("Order_Date",mOrdArr.get(i).getorderDate());
ordObj.put("Customer_id",mOrdArr.get(i).getCustPKID());
Customer aCust = db.getEmployee(mOrdArr.get(i).getCustPKID());
ordObj.put("Cust_name",aCust.getEmpName());// query DB
ordObj.put("Company_id",sharedpreferences.getString(OrderApplication.CompanyID,"")); // sharedP
ordObj.put("Device_Ref",mOrdArr.get(i).getOrdPKID());// sharedP
ordObj.put("User_ID",sharedpreferences.getString(OrderApplication.UserID,""));// sharedP
JSONArray prodJsonArray = new JSONArray();
ArrayList<Product> mProdArr = db.getAllProductOrder(mOrdArr.get(i).getorderID());
for (int j=0; j<mProdArr.size();j++) {
JSONObject prodObj = new JSONObject();
prodObj.put("Product_id",mProdArr.get(j).getPrID());
prodObj.put("Product_name",mProdArr.get(j).getprName());
prodObj.put("Product_Brand",mProdArr.get(j).getBrandName());
prodObj.put("Qty",mProdArr.get(j).getPrQty());
prodObj.put("Rate",(Double.parseDouble(mProdArr.get(j).getPrAmt()+"")/ mProdArr.get(j).getPrQty()));
prodObj.put("Total_Amount",(Double.parseDouble(mProdArr.get(j).getPrAmt()+"")));
prodJsonArray.put(j, prodObj);
}
ordObj.put("OrderDetails",prodJsonArray);
ordJsonArray.put(i,ordObj);
}
ordJsonObj.put("Orders",ordJsonArray);
Log.d("response", "" + ordJsonObj.toString());
I have written the following retrofit code to post the json object but with this following code I am getting
failure -> error : 400 Bad Request.
RestAdapter adapter = new RestAdapter.Builder()
.setEndpoint(OrderApplication.getBase_URL)
.build();
//Creating object for our interface
syncinter api = adapter.create(syncinter.class);
api.sync_data(ordJsonObj, new Callback<JsonObject>() {
#Override
public void success(JsonObject jsonObject, retrofit.client.Response response) {
}
#Override
public void failure(RetrofitError error) {
Log.d("ERROR", String.valueOf(error));
Toast.makeText(getActivity(),"Order failed to place on Server",Toast.LENGTH_LONG).show();
}
});
i was able to post it using TypedInput declare the api as shown below
#PUT(ServerEndPoint)
void callApi(#Body TypedInput input, Callback<Response> response);
and send the json object like this
TypedInput input = null;
try {
JSONObject obj = new JSONObject();
obj.put("KEY", "value");
input = new TypedByteArray("application/json", obj.toString().getBytes("UTF-8"));
} catch (Exception e) {
e.printStackTrace();
}
callApi(input, new Callback<Response>() {
#Override
public void success(Response response, Response response2) {
}
#Override
public void failure(RetrofitError error) {
}
});
not of relative importance i am using retrofit 1.9
I am using retrofit to get data from http URL.
My Interface Class :
public interface SlotsAPI {
/*Retrofit get annotation with our URL
And our method that will return a Json Object
*/
#GET(url)
retrofit.Call<JSONObject> getSlots();
}
My request method.
public void getResponse(){
Retrofit retrofit = new Retrofit.Builder()
.baseUrl(URL)
.addConverterFactory(GsonConverterFactory.create())
.build();
//Creating an object of our api interface
SlotsAPI api = retrofit.create(SlotsAPI.class);
retrofit.Call<JSONObject> callback = api.getSlots();
callback.enqueue(new Callback<JSONObject>() {
#Override
public void onResponse(Response<JSONObject> response) {
if (response != null) {
Log.d("OnResponse", response.body().toString());
}
}
#Override
public void onFailure(Throwable t) {
t.printStackTrace();
}
});
}
In the response I am receiving an empty body.And the server responds with 200 OK.
D/OnResponse: {}
But when I open the URL in browser I am getting JSONObject on the screen.
you should try like this way ....
public interface SlotsAPI {
/*Retrofit get annotation with our URL
And our method that will return a Json Object
*/
#GET(url)
Call<JsonElement> getSlots();
}
in request method
retrofit.Call<JsonElement> callback = api.getSlots();
callback.enqueue(new Callback<JsonElement>() {
#Override
public void onResponse(Response<JsonElement> response) {
if (response != null) {
Log.d("OnResponse", response.body().toString());
}
}
Please check your JsonObject. If you want to get response in json you must be define a response type JsonObject not JSONObject other wise specify the pojo class in your interface.
I think you are not understanding the retrofit filosofy.
The correct interface should be:
public interface SlotsAPI {
/*Retrofit get annotation with our URL
And our method that will return a Json Object
*/
#GET(url)
JSONObject getSlots();
}
When you call the getSlots method, retrofit will automatically do the HTTP request and return the JSONObject.
You will need to do this out of the main thread.
Make sure that the url of #Get is relative path
#Base URL: always ends with /
#Url: DO NOT start with /
Example:
String URL = http://api.co/base/ ;
And
#GET("webservice/syncdown")
JSONObject getSlots();
You may receiving a list of Slots. the Gson converter will handle it if you sending array of json
#GET(url)
retrofit.Call<List<Slot>> getSlots();
You are using the retrofit 2 or 1? The version 2 still is in beta.
If you are using the version 1. Use this:
public interface SlotsAPI {
/*Retrofit get annotation with our URL
And our method that will return a Json Object
*/
#GET(url)
void getSlots(Callback<JsonElement> callback);
}
With this the call will be asynchronous.
Same problem here, and answer from curiousMind saved my day.
More on the same subject: if you need to get a value from a pair use:
String value = response.body().getAsJsonObject().get("pair_name").getAsString();
Call<Void> getSlots() worked for me.
private void APIRetrofit_method() {
Retrofit retrofit = new Retrofit.Builder()
.baseUrl(RecyclerInterface.JSONURL)
// .client(okHttpClient)
.addConverterFactory(GsonConverterFactory.create())
.build();
RecyclerInterface api = retrofit.create(RecyclerInterface.class);
Call<ResponseBody> call = api.getString(); /// GET METHOD without passing params
// Post METHOD CODE START
// HashMap<String, String> params = new HashMap<String, String>();
// params.put("name", "yuva");
// params.put("pass", "" + "123");
// Call<ResponseBody> call1 = api.getProspectList(params);
// Post METHOD CODE END
call.enqueue(new Callback<ResponseBody>() {
#Override
public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
try {
Log.d(TAG, "GetProspectlistresponse" + "" + response.isSuccessful());
utility.hideProgressDialog();
if (response.isSuccessful()) {
String remoteResponse = new String(response.body().string());
Log.d(TAG, "Holidaylistresponse" + "" + remoteResponse);
try {
JSONObject object = new JSONObject(remoteResponse);
JSONArray array = object.getJSONArray("Holidays_Details");
if (array.toString().equals("[]")) {
holiday_recyclerView.setVisibility(View.GONE);
} else {
holiday_recyclerView.setVisibility(View.VISIBLE);
for (int i = 0; i < array.length(); i++) {
JSONObject c = array.getJSONObject(i);
String holidayDate = c.getString(TAG_HOLIDAYDATE);
String holidayName = c.getString(TAG_HOLIDAYName);
String holidaytype = c.getString(TAG_HOLIDAYtype);
HashMap<String, String> customers = new HashMap<String, String>();
customers.put(TAG_HOLIDAYDATE, holidayDate);
customers.put(TAG_HOLIDAYName, holidayName);
customers.put(TAG_HOLIDAYtype, holidaytype);
arrayList.add(customers);
}
getHolidaylistAdapter.notifyDataSetChanged();
}
} catch (JSONException e) {
e.printStackTrace();
}
} else {
utility.hideProgressDialog();
}
} catch (IOException e) {
e.printStackTrace();
}
#Override
public void onFailure(Call<ResponseBody> call, Throwable t) {
Log.i("ErrorResponsestring", call.toString());
}
});
}
String JSONURL = "https://demonuts.com/Demonuts/JsonTest/Tennis/";
#GET("json_parsing.php")
Call<ResponseBody> getString();
// #POST("getProspectList")
// #FormUrlEncoded
// Call<ResponseBody> getProspectList(#FieldMap HashMap<String, String> body);
implementation 'com.squareup.retrofit2:retrofit:2.0.2'
implementation 'com.squareup.retrofit2:converter-gson:2.0.2'
implementation 'com.squareup.okhttp3:okhttp:4.0.0'