2016-07-19 212 views
10

Sto utilizzando Retrofit2 e voglio sovrascrivere il suo metodo Call.enqueue.Come eseguire un'implementazione personalizzata di Retrofit2.Call <T>

ho fatto finora:

personalizzata chiamata:

public class CustomCall<T> implements Call<T> { 

     private final Call<T> delegate; 
     //..every method has delegate method invoked in it 

Apis:

 @GET 
     CustomCall<TKBaseResponse> testConnection(@Url String customUrl); 

Ma io continuo a ricevere questi errori:

Unable to create call adapter for CustomCall<....> 

e

Could not locate call adapter for CustomCall<....> 

qualsiasi modo su come posso fare questo in modo corretto? Grazie in anticipo!

+0

si può iniziare mostrando il resto del codice di chiamata, ed i log degli errori completi –

+0

perché u necessario creare CustomCall?basta creare qualsiasi classe di interfaccia che contenga una semplice chiamata con dovrebbe essere sufficiente per creare qualsiasi applicazione che si connetta a qualsiasi webservice, non è vero? – faruk

+0

Si prega di dare un'occhiata da qui https://github.com/saveendhiman/SampleApp/tree/master/app/src/main/java/com/sampleapp/api – Saveen

risposta

1

Sto postando un esempio per aiutarti con l'implementazione del retrofit.

Crea la tua risorsa come questa (MyResource.java).

Call<TKBaseResponse> testConnection(@@Url String customUrl); 

inizializzazione Retrofit

private Resource getRetrofitResource(){ 
    //Initialize retrofit. 
    final Retrofit = .....//your code to initialize retrofit 
    return retrofit.create(MyResource.class); 
} 

Per implementare chiamata Enqueue (chiamate asincrone retrofit) è necessario passare la vostra risposta di risorse e un gestore di risposta che è la vostra implementazione personalizzata nel metodo Enqueue. Sto postando la mia implementazione di ResponseHandler a fianco.

public abstract class ResponseHandler<T> { 

    private static final String TAG = ResponseHandler.class.getSimpleName(); 

    private static final String LINE_SEPARATOR = System.getProperty("line.separator"); 

    private final Context context; 

    public ResponseHandler() { 
     this(null); 
    } 

    public ResponseHandler(final Context context) { 
     this.context = context; 
    } 


    public abstract void onResponse(final T response); 

    public void onError(final ErrorResponse errorResponse) { 
     if (context == null) { 
      return; 
     } 
     Log.e(TAG, "An error occurred while invoking service. Error Code: " + errorResponse.getErrorCode() + LINE_SEPARATOR + "Message: " + errorResponse.getMessage() + LINE_SEPARATOR); 
     final AlertDialog.Builder alertBuilder = new AlertDialog.Builder(context); 
     alertBuilder.setCancelable(true); 
     alertBuilder.setTitle(R.string.title_server_error_dialog); 
     alertBuilder.setMessage(R.string.network_error_message); 
     alertBuilder.setPositiveButton(R.string.text_ok, new DialogInterface.OnClickListener() { 
      @Override 
      public void onClick(final DialogInterface dialog, final int which) { 
       dialog.dismiss(); 
      } 
     }); 
     alertBuilder.show(); 
    } 

    public void onFailure(Throwable throwable) { 
     if (context == null) { 
      return; 
     } 
     Log.e(TAG, "An error occurred while invoking service", throwable); 
     final AlertDialog.Builder alertBuilder = new AlertDialog.Builder(context); 
     alertBuilder.setCancelable(true); 
     alertBuilder.setTitle(R.string.title_network_error_dialog); 
     alertBuilder.setMessage(R.string.network_error_message); 
     alertBuilder.setPositiveButton(R.string.text_ok, new DialogInterface.OnClickListener() { 
      @Override 
      public void onClick(final DialogInterface dialog, final int which) { 
       dialog.dismiss(); 
      } 
     }); 
     alertBuilder.show(); 
    } 

} 

Creare una risposta di handle di metodo.

protected <T> void handleResponse(Call<T> call, final ResponseHandler<T> responseHandler) { 
     call.enqueue(new Callback<T>() { 
      @Override 
      public void onResponse(final Call<T> call, final Response<T> response) { 
       if (response.isSuccess()) { 
       if (responseHandler != null) { 
        responseHandler.onResponse(response.body()); 
       } 
      } else { 
       final ErrorResponse errorResponse = parseError(response); 
       if (responseHandler != null) { 
        responseHandler.onError(errorResponse); 
       } 
      } 
      } 

      @Override 
      public void onFailure(final Call<T> call, final Throwable throwable) { 
       if (responseHandler != null) { 
       responseHandler.onFailure(throwable); 
      } 
      } 
     }); 
    } 

Per favore fatemi sapere se avete qualche dubbio su questo.

Ora da chiamare la tua risorsa come di seguito.

final MyResource resource = getRetrofitResource(); 
final Call<TKBaseResponse> response = resource .testConnection("ANY_URL_OF_YOUR_CHOICE"); 
handleResponse(response, new ResponseHandler<TKBaseResponse>(){ 

public void onResponse(final TKBaseResponse response){ 
     //Do whatever you want to do here.. 
} 
    }); 
+0

Da quale libreria è ** Resource **? –

+0

MyResource non è altro che una semplice interfaccia java. puoi seguire il link sottostante per più approfondimenti. http://www.vogella.com/tutorials/Retrofit/article.html Cercherò di dedicare un po 'di tempo e preparare un progetto git per dimostrare un utilizzo molto semplice con una struttura di codice adeguata. Grazie –

+0

Questo non risponde alla mia domanda su come posso ignorare la funzione di accodamento della chiamata

5

Innanzitutto creare una classe ServiceManager -

public final class ServiceManager { 

    private static ServiceManager sServiceManager; 

    /** 
    * Gets the instance of the web services implementation. 
    * 
    * @return the singleton instance. 
    */ 
    public static ServiceManager get() { 
     if (sServiceManager == null) { 
      sServiceManager = new ServiceManager(); 
     } 
     return sServiceManager; 
    } 

    /** 
    * Creates the services for a given HTTP Url, useful when testing 
    * through multiple endpoints and unit testing 
    * 
    * @param clazz the service class. 
    * @param <T> type of the service. 
    * @return the created services implementation. 
    */ 
    public <T> T createService(Class<T> clazz) { 
     return createService(clazz, HttpUrl.parse(ServiceApiEndpoints.SERVICE_ENDPOINT)); 
    } 

    /** 
    * Creates the services for a given HTTP Url, useful when testing 
    * through multiple endpoints and unit testing 
    * 
    * @param clazz the service class. 
    * @param httpUrl the endpoint 
    * @param <T>  type of the service. 
    * @return the created services implementation. 
    */ 
    public <T> T createService(Class<T> clazz, HttpUrl httpUrl) { 
     Retrofit retrofit = getRetrofit(httpUrl); 
     return retrofit.create(clazz); 
    } 

    public <T> T createService(Class<T> clazz, Retrofit retrofit) { 
     return retrofit.create(clazz); 
    } 

    private Retrofit getRetrofit(HttpUrl httpUrl) { 
     return new Retrofit.Builder() 
       .baseUrl(httpUrl) 
       .client(createClient()) 
       .addConverterFactory(getConverter()) 
       .build(); 
    } 

    public Retrofit getPlainRetrofit(HttpUrl httpUrl) { 
     return new Retrofit.Builder() 
       .baseUrl(httpUrl) 
       .client(new OkHttpClient.Builder().build()) 
       .addConverterFactory(getConverter()) 
       .build(); 
    } 

    private Converter.Factory getConverter() { 
     return GsonConverterFactory.create(); 
    } 


    private OkHttpClient createClient() { 
     return new OkHttpClient.Builder().addInterceptor(new RequestInterceptor()).build(); 
    } 

} 

ServiceApiEndpoints è una classe contiene endpoint del servizio.

final class ServiceApiEndpoints { 

    public static final String SERVICE_ENDPOINT = "your_app_url"; 
} 

Creare un APIService un'interfaccia

public interface APIService { 
String GET_INFO = "get_info"; 

    @GET(GET_INFO) 
    Call<ResInfo[]> getInfo(); 
} 

Crea modello ResInfo.

public class ResInfo { 
    private static final String FIELD_CONTENT = "content"; 

    public String getContent() { 
     return mContent; 
    } 

    public void setContent(final String content) { 
     mContent = content; 
    } 


    @SerializedName(FIELD_CONTENT) 
    private String mContent; 

    public ResInfo(){ 

    } 
} 

Chiamare la richiesta.

private Call<ResInfo[]> mGetInfoAPICall; 

    APIService apiService=ServiceManager.get().createService(APIService.class); 
    mGetInfoAPICall = apiService.getInfo(); 
    mGetInfoAPICall.enqueue(new Callback<ResInfo[]>() { 
    @Override 
    public void onResponse(Call<ResInfo[]> call, Response<ResInfo[]> response) { 

    } 

    @Override 
    public void onFailure(Call<ResInfo[]> call, Throwable t) { 

    } 
}); 
Problemi correlati