how to use Retrofit for post request from Server? - android

This is my url http://192.168.1.217:8088/api/frontend/web/index.php?r=api/sms/send,and I need take some params,the following is param
{"body":{"param":"VjvBNGoYQ3/nCytxN0zx5rr+6sewp7FABok5N3DdDdD0WWu7KCCohA=="},
"header":{"deviceId":"","appToken":"","serviceCode":"sms","appType":1,"appVersion":1,"clientType":1}}
I shoud how write the code use retrofit?Thanks advanced.

This is the best example I have found on how to use retrofit so far http://www.androidhive.info/2016/05/android-working-with-retrofit-http-library/
But if you want to another example here is the code i used for OpenWeatherMap.
public class ApiClient {
private static final int TIME_OUT = 30;
public static final String BASE_URL = "http://api.openweathermap.org/";
private static Retrofit retrofit = null;
public static Retrofit getClient() {
if (retrofit==null) {
OkHttpClient.Builder okBuilder = new OkHttpClient.Builder();
okBuilder.connectTimeout(TIME_OUT, TimeUnit.SECONDS);
okBuilder.readTimeout(TIME_OUT, TimeUnit.SECONDS);
okBuilder.writeTimeout(TIME_OUT, TimeUnit.SECONDS);
Gson gson = new GsonBuilder().create();
return new Retrofit.Builder()
.baseUrl(BASE_URL) .addConverterFactory(ScalarsConverterFactory.create())
.addConverterFactory(GsonConverterFactory.create(gson))
.client(okBuilder.build())
.build();
}
return retrofit;
}
public interface ApiInterface {
#GET("data/2.5/forecast?id=524901")
Call<WeatherResponse> getWeatherData(#Query("APPID") String apiKey);
}

Related

Send Json with formated Date

I am trying to send Json with formated Date (pattern="yyyy-MM-dd HH:mm:ss").The problem is that server don't recognize this pattern and give error java.io.EOFException: \n not found: limit=1 content=0d… I tried add GsonBuilder in RetrofitClient class, but it doesn't worked.
String mobileDate= (String) android.text.format.DateFormat.format("yyyy-MM-dd HH:mm:ss", new java.util.Date());
RetrofitClient
public class RetrofitClient {
private static Retrofit retrofit=null;
private static String base_url= null;
public static void setBaseUrl(String string){
base_url = string;
}
public static void deletePreviousInstance(){
retrofit=null;
}
public static Retrofit getRetrofitInstance(){
if(retrofit==null){
Gson gson = new GsonBuilder()
.setDateFormat("yyyy-MM-dd HH:mm:ss")
.create();
OkHttpClient okHttpClient = new OkHttpClient().newBuilder()
.connectTimeout(25, TimeUnit.SECONDS)
.readTimeout(25, TimeUnit.SECONDS)
.writeTimeout(25, TimeUnit.SECONDS)
.build();
retrofit= new Retrofit.Builder()
.baseUrl(base_url)
.client(okHttpClient)
.addConverterFactory(GsonConverterFactory.create(gson))
.build();
}
return retrofit;
}
}
you are giving a string as parameter for date format you have to parse the same date format at the server end. you can check out this link https://stackoverflow.com/a/882465/2285117

How to solve failed connection to service?

I want to get to the service in specific URL .... I use retrofit to get it but it give me an error connection to the URL...while the URL is active in chrome.
in the code I write ??? instead to correct one ^__^ (this code is class APIClient)
and to be sure that I work in correct way I was built an api in mocky site with the same json file .... and it is work
so can any one help me please
public static final String BASE_URL = "http://111.222.1.12:0000/???/???/????/";
//database
public static final String BASE_URL2 = "http://www.mocky.io/v2/";
public static Boolean URL=true;
private static Retrofit retrofit = null;
public static Retrofit getClient(){
if (retrofit==null) {
if(URL)
{
retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.build();
}
else
{
retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL2)
.addConverterFactory(GsonConverterFactory.create())
.build();
}
}
return retrofit;
}
Hello you can try using my ApiClient, I'm using rxJava so you need to redesign the APIClient to your need
public class ApiClient {
private static Retrofit retrofit = null;
private static int REQUEST_TIMEOUT = 120;
private static OkHttpClient okHttpClient;
public static Retrofit getClient(Context context) {
if (okHttpClient == null)
initOkHttp(context);
if (retrofit == null) {
retrofit = new Retrofit.Builder()
.baseUrl(API_PATH)
.client(okHttpClient)
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())
.addConverterFactory(GsonConverterFactory.create())
.build();
}
return retrofit;
}
private static void initOkHttp(Context context) {
ConnectionSpec spec = new ConnectionSpec.Builder(ConnectionSpec.MODERN_TLS)
.tlsVersions(TlsVersion.TLS_1_2)
.cipherSuites(
CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,
CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256)
.build();
OkHttpClient.Builder httpClient = new OkHttpClient().newBuilder()
.connectTimeout(REQUEST_TIMEOUT, TimeUnit.SECONDS)
.readTimeout(REQUEST_TIMEOUT, TimeUnit.SECONDS)
.writeTimeout(REQUEST_TIMEOUT, TimeUnit.SECONDS);
HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor();
interceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
httpClient.addInterceptor(interceptor);
httpClient.addInterceptor(new Interceptor() {
#Override
public Response intercept(Chain chain) throws IOException {
Request original = chain.request();
Request.Builder requestBuilder = original.newBuilder()
.addHeader("Accept", "application/json")
.addHeader("Request-Type", "Android")
.addHeader("Content-Type", "application/json");
Request request = requestBuilder.build();
return chain.proceed(request);
}
});
okHttpClient = httpClient.build();
}
public static void resetApiClient() {
retrofit = null;
okHttpClient = null;
}
}
Hope this reference can help you solve your problems

Is it possible to use multiple baseurl in retrofit?

I want to use two server url using retrofit, but only one is working when I am using two base url. Please tell me how to use two base url in android.
public class APIUtils {
public static String Url1 = "http://10.0.13.46:19460";
public static String Url12 = "http://freshcamera.herokuapp.com";
public static SOService getSOService(String url) {
return RetrofitClient.getClient(url1).create(SOService.class);
}
}
SOService class
public interface SOService {
//URL 2
#FormUrlEncoded
#POST("/api/user/LoginUser")
Call<Login> Login(#Field("username") String username, #Field("password")String password, #Field("grant_type")String passwords);
}
SOService_AI class
public interface SOService_AI {
//URL 1
#FormUrlEncoded
#POST("/finalresult1")
Call<List<AIImageProcessing>> AiImageCheck(#Field("img_data") String imgdata, #Field("name")String imgName);
}
I guess what you need is changing URL at runtime to a completely different one.
For example, the following code will override the URL passed as baseUrl to retrofit object.
#GET
public Call<ResponseBody> profilePicture(#Url String url);
Note: You can't add url param to #GET and #POST. The URL must be passed to #Url.
// ERROR ( #Url cannot be used with #GET URL)
#GET("users") // or POST
public Call<Foo> getUsers(#Url String url);
// CORRECT
#GET
public Call<Foo> getUsers(#Url String fullUrl);
Checkout this tutorial for further information.
if you are working two url then you create two retrofit object. because single retrofit object work on single url.
if you want to access two your make two retofit object like below code..
public class ApiClient {
private final static String BASE_URL = "https://simplifiedcoding.net/demos/";
private final static String BASE_URL2 = "http://freshcamera.herokuapp.com";
public static ApiClient apiClient;
private Retrofit retrofit = null;
private Retrofit retrofit2=null;
public static ApiClient getInstance() {
if (apiClient == null) {
apiClient = new ApiClient();
}
return apiClient;
}
//private static Retrofit storeRetrofit = null;
public Retrofit getClient() {
return getClient(null);
}
public Retrofit getClient2() {
return getClient2(null);
}
private Retrofit getClient(final Context context) {
HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor();
interceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
OkHttpClient.Builder client = new OkHttpClient.Builder();
client.readTimeout(60, TimeUnit.SECONDS);
client.writeTimeout(60, TimeUnit.SECONDS);
client.connectTimeout(60, TimeUnit.SECONDS);
client.addInterceptor(interceptor);
client.addInterceptor(new Interceptor() {
#Override
public okhttp3.Response intercept(Chain chain) throws IOException {
Request request = chain.request();
return chain.proceed(request);
}
});
retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.client(client.build())
.addConverterFactory(GsonConverterFactory.create())
.build();
return retrofit;
}
private Retrofit getClient2(final Context context) {
HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor();
interceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
OkHttpClient.Builder client = new OkHttpClient.Builder();
client.readTimeout(60, TimeUnit.SECONDS);
client.writeTimeout(60, TimeUnit.SECONDS);
client.connectTimeout(60, TimeUnit.SECONDS);
client.addInterceptor(interceptor);
client.addInterceptor(new Interceptor() {
#Override
public okhttp3.Response intercept(Chain chain) throws IOException {
Request request = chain.request();
return chain.proceed(request);
}
});
retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL2)
.client(client.build())
.addConverterFactory(GsonConverterFactory.create())
.build();
return retrofit;
}
}
then after access like below code ..
ApiClient.getInstance().getClient();
ApiClient.getInstance().getClient2();
with Kotlin its even easier
companion object {
// init Retrofit base server instance
val redditClient by lazy { ApiService.invoke(REDDIT_BASE_URL) }
val stackClient by lazy { ApiService.invoke(STACK_BASE_URL) }
private val loggingInterceptor = HttpLoggingInterceptor().apply {
this.level = HttpLoggingInterceptor.Level.BODY
}
operator fun invoke(baseUrl: String): ApiService {
val client = OkHttpClient.Builder().apply {
/**addNetworkInterceptor(StethoInterceptor()) */
addNetworkInterceptor(loggingInterceptor)
connectTimeout(10, TimeUnit.MINUTES)
readTimeout(10, TimeUnit.MINUTES)
writeTimeout(10, TimeUnit.MINUTES)
}.build()
return Retrofit.Builder()
.client(client)
.baseUrl(baseUrl)
.addCallAdapterFactory(CoroutineCallAdapterFactory())
.addConverterFactory(GsonConverterFactory.create())
.build()
.create(ApiService::class.java)
}
}
just pass the baseUrl in the invoke method
This is really easy now
Simply use Post or Get without a constant url instead accept it in a parameter and annotate that parameter with #Url
#GET
suspend fun handshakeUser(#Url url : String): Response<JsonObject>
#POST
suspend fun makePostRequest(
#Header("Authorization") token: String = getToken(),
#Url url: String,
#Body inputModel: JsonObject
): Response<JsonObject>

How to set header to all of requests?

In my application I used Retrofit for get requests from server.
I want set header to all of requests, I write below codes :
public class ApiClient {
private static final String BASE_URL = "http://example.com/api/v1.0.0.1/Api/";
private static Retrofit retrofit = null;
public static Gson gson = new GsonBuilder().create();
public static Retrofit getClient() {
HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor();
interceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
OkHttpClient.Builder builder = new OkHttpClient.Builder();
builder.interceptors().add(interceptor);
builder.addInterceptor(new Interceptor() {
#Override
public Response intercept(Interceptor.Chain chain) throws IOException {
Request request = chain.request().newBuilder().addHeader("Device", "2").build();
return chain.proceed(request);
}
});
OkHttpClient client = builder
.connectTimeout(120, TimeUnit.SECONDS)
.writeTimeout(120, TimeUnit.SECONDS)
.readTimeout(120, TimeUnit.SECONDS)
.build();
if (retrofit == null) {
retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create(gson))
.client(client)
.build();
}
return retrofit;
}
}
But when run application, not set this header!
How can I it? please help me

Code implementation Singleton Design Pattern: Bill Pugh on a Retrofit object

I have been trying to implement the Bill Pugh Singleton Design Pattern using a private static class to return the singleton retrofit instance. SO far I have been able to come up with the following code. Can someone help me review this code and confirm if this is a proper implementation of the singleton design pattern suggested by Mr. Bill Pugh Himself or suggest me a proper way of implementing this.
public class SingletonRetrofit {
private SingletonRetrofit(){}
private static class SingletonRetrofitHelper {
private static OkHttpClient okHttpClient;
private static Retrofit retrofit;
private static Retrofit makeRetrofit() {
HttpLoggingInterceptor interceptor = new HttpLoggingInterceptor();
interceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
okHttpClient = new OkHttpClient.Builder()
.addInterceptor(interceptor)
.readTimeout(20, TimeUnit.SECONDS)
.connectTimeout(15, TimeUnit.SECONDS)
.build();
retrofit = new Retrofit.Builder()
.baseUrl("http://ci.draftserver.com/hornsbyapp/webservice/")
.client(okHttpClient)
.addConverterFactory(ScalarsConverterFactory.create())
.addConverterFactory(GsonConverterFactory.create())
.build();
return retrofit;
}
}
public static Retrofit getInstance() {
return SingletonRetrofitHelper.makeRetrofit();
}
}
USE this one:
public class Apiclient {
private static final String BASE_URL ="URL";
private static Retrofit retrofit = null;
public static Retrofit getClient() {
if (retrofit == null) {
OkHttpClient.Builder httpClient2 = new OkHttpClient.Builder();
httpClient2.addNetworkInterceptor(new Interceptor() {
#Override
public Response intercept(Chain chain) throws IOException {
Request.Builder builder = chain.request().newBuilder();
builder.addHeader("site_id","1");
return chain.proceed(builder.build());
}
});
OkHttpClient client = httpClient2.build();
retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.client(client)
.addConverterFactory(GsonConverterFactory.create())
.build();
}
return retrofit;
}
}

Categories

Resources