Reputation: 267
I am trying to use Retrofit and RxJava to make an API call within a custom view in an app that I am working on, but I encounter an incompatible type error when trying to subscribe to the Observable from my Retrofit API call.
My retrofit interface:
public interface ApiQueryInterface{
// Request method and URL specified in the annotation
// Callback for the parsed response is the last parameter
@GET("users/")
Observable<Users> getUsers (
@Query("key") String key,
@Query("address") String address
);
@GET("posts/")
Observable<Posts> getPosts (
@Query("key") String key,
@Query("address") String address
);
}
and the Retrofit call located within the onFinishInflate() of the custom view:
// Create RxJava adapter for synchronous call
RxJava2CallAdapterFactory rxAdapter = RxJava2CallAdapterFactory.create();
// Create Retrofit2 instance for API call
Retrofit retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.addCallAdapterFactory(rxAdapter)
.build();
// Make API call using retrofit
final ApiQueryInterface apiQueryInterface = retrofit.create(ApiQueryInterface.class);
// API return type defined by interface
Observable<Users> query = apiQueryInterface
.getUsers(KEY, ADDRESS)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<Users>() {
@Override
public void onSubscribe(Disposable d) {
}
@Override
public void onNext(Users users) {
}
@Override
public void onError(Throwable e) {
}
@Override
public void onComplete() {
}
});
}
When I build the project I hit an incompatible types error in the custom view on the line beginning with Observable<Users> query = ...:
Error:(60, 27) error: incompatible types: void cannot be converted to Observable<Users>
"Users" is a generic model class which matches the JSON object returned from the API
Upvotes: 4
Views: 4252
Reputation: 2992
Change returned object to Subscription
private Subscription subscription;
....
subscription = ApiClient.getInstance()
.getUsers(KEY, ADDRESS)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<List<Users>>() {
@Override public void onCompleted() {
}
@Override public void onError(Throwable e) {
}
@Override public void onNext(List<Users> users) {
}
});
apiclient
public class ApiClient {
private static ApiClient instance;
private ApiQueryInterface apiqueryinterface;
private ApiClient() {
final Gson gson =
new GsonBuilder().setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES).create();
final Retrofit retrofit = new Retrofit.Builder().baseUrl(BASE_URL)
.addCallAdapterFactory(RxJavaCallAdapterFactory.create())
.addConverterFactory(GsonConverterFactory.create(gson))
.build();
apiqueryinterface = retrofit.create(ApiQueryInterface.class);
}
public static ApiClient getInstance() {
if (instance == null) {
instance = new ApiClient();
}
return instance;
}
public Observable<List<Users>> getUsers(@NonNull String key, @NonNull String address) {
return apiqueryinterface.getUsers(key, address);
}
}
interface
public interface ApiQueryInterface{
// Request method and URL specified in the annotation
// Callback for the parsed response is the last parameter
@GET("users")
Observable<<List<Users>> getUsers (
@Query("key") String key,
@Query("address") String address
);
Upvotes: 0
Reputation: 157437
RxJava 1
returns a Subscription
object not an Observable
. RxJava 2
subscription returns void. That's why you are getting Error:(60, 27) error: incompatible types
. You are getting the Disposable in the callback onSubscribe
. If you need a reference to it, you can assign it to a class level member when the callback is invoked
Upvotes: 2