2015-01-08 8 views
11

での取り扱い:(による非推奨に)アンドロイドrxJavaエラー私はこれを使用する代わりに</p> <pre><code>Observable.create(new Observable.OnSubscribeFunc<T>() {...}); </code></pre> <p>の新しいRXのJavaを使用しています改造

Observable.create(new Observable.OnSubscribe<T>() {...}); 

を(これが最もとして重要になることが例、チュートリアル、explonationは古いものを使用しています...)

さて、私の問題を見てみましょう。私はJavaクラスを持っており、そこから関連する部分があります。

private interface ApiManagerService { 

    @FormUrlEncoded 
    @POST("/login") 
    User getUser(@Field("username") String userName, @Field("password") String password); 

} 


private static RestAdapter restAdapter = new RestAdapter.Builder() 
    .setEndpoint(HOST) 
    .setLogLevel(RestAdapter.LogLevel.FULL) 
    .build(); 

private static ApiManagerService apiManager = restAdapter.create(ApiManagerService.class); 

public static Subscription login(final String userName, final String password, Observer<User> observer) { 
    return Observable.create(new Observable.OnSubscribe<User>() { 
     @Override 
     public void call(Subscriber<? super User> subscriber) { 
      try { 

       User user = apiManager.getUser(userName, password); 

       subscriber.onNext(user); 
       subscriber.onCompleted(); 

      } catch (RetrofitError e) { 
       subscriber.onError(e); 
      } catch (Throwable e) { 
       subscriber.onError(e); 
      } 
     } 
    } 

    ).subscribeOn(Schedulers.io()) 
    .retry(3) 
    .observeOn(AndroidSchedulers.mainThread()) 
    .subscribe(observer); 
} 

このコードはすべて正常であればほとんど完全に動作します。しかし、私が意図的にエラーを起こすと、WiFiをオフにするのと同じように、"UnKnownHostException" ... try catchブロックの改造呼び出し(getUser)で発生するはずです。しかし、私が処理できるonError(Throwable t) - >にエラーを処理する代わりに、アプリケーションをクラッシュさせます。したがって、エラーがcatchブロックに到達しないような場合です。 HTTPエラー(404,401など)がキャッチされていて、onError(...)が取得していて、すべて正常です。

クラッシュする前にすべてが3回進み、.retry(3)の時点ではcatch節には入りません。

EDIT 1

LogCat出力:

01-08 16:19:31.576 15285-16162/asd.bdef.gh D/Retrofit﹕ ---- ERROR https://testapi.com/api/login 
    01-08 16:19:31.606 15285-16162/asd.bdef.gh D/Retrofit﹕ java.net.UnknownHostException: Unable to resolve host "testapi.com": No address associated with hostname 
       at java.net.InetAddress.lookupHostByName(InetAddress.java:394) 
       at java.net.InetAddress.getAllByNameImpl(InetAddress.java:236) 
       at java.net.InetAddress.getAllByName(InetAddress.java:214) 
       at com.squareup.okhttp.internal.Network$1.resolveInetAddresses(Network.java:29) 
       at com.squareup.okhttp.internal.http.RouteSelector.resetNextInetSocketAddress(RouteSelector.java:259) 
       at com.squareup.okhttp.internal.http.RouteSelector.nextProxy(RouteSelector.java:233) 
       at com.squareup.okhttp.internal.http.RouteSelector.nextUnconnected(RouteSelector.java:159) 
       at com.squareup.okhttp.internal.http.RouteSelector.next(RouteSelector.java:133) 
       at com.squareup.okhttp.internal.http.HttpEngine.connect(HttpEngine.java:314) 
       at com.squareup.okhttp.internal.http.HttpEngine.sendRequest(HttpEngine.java:237) 
       at com.squareup.okhttp.internal.huc.HttpURLConnectionImpl.execute(HttpURLConnectionImpl.java:423) 
       at com.squareup.okhttp.internal.huc.HttpURLConnectionImpl.connect(HttpURLConnectionImpl.java:105) 
       at com.squareup.okhttp.internal.huc.HttpURLConnectionImpl.getOutputStream(HttpURLConnectionImpl.java:239) 
       at com.squareup.okhttp.internal.huc.DelegatingHttpsURLConnection.getOutputStream(DelegatingHttpsURLConnection.java:218) 
       at com.squareup.okhttp.internal.huc.HttpsURLConnectionImpl.getOutputStream(HttpsURLConnectionImpl.java:25) 
       at retrofit.client.UrlConnectionClient.prepareRequest(UrlConnectionClient.java:68) 
       at retrofit.client.UrlConnectionClient.execute(UrlConnectionClient.java:37) 
       at retrofit.RestAdapter$RestHandler.invokeRequest(RestAdapter.java:321) 
       at retrofit.RestAdapter$RestHandler.access$100(RestAdapter.java:220) 
       at retrofit.RestAdapter$RestHandler$1.invoke(RestAdapter.java:265) 
       at retrofit.RxSupport$2.run(RxSupport.java:55) 
       at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:390) 
       at java.util.concurrent.FutureTask.run(FutureTask.java:234) 
       at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1080) 
       at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:573) 
       at retrofit.Platform$Android$2$1.run(Platform.java:142) 
       at java.lang.Thread.run(Thread.java:841) 
    01-08 16:19:31.606 15285-16162/asd.bdef.gh D/Retrofit﹕ ---- END ERROR 
    01-08 16:19:31.977 15285-15285/asd.bdef.gh D/AndroidRuntime﹕ Shutting down VM 
    01-08 16:19:31.977 15285-15285/asd.bdef.gh W/dalvikvm﹕ threadid=1: thread exiting with uncaught exception (group=0x41c9d8b0) 
    01-08 16:19:31.977 15285-15285/asd.bdef.gh E/AndroidRuntime﹕ FATAL EXCEPTION: main 

は、与えられたAPIアドレスが本物ではありませんが、本当の一つが到達可能です。エラー処理をテストするためにWiFiをオフにしました。

もう1つのユースケース:observable .onExceptionResumeNext([第2 observable])に追加すると、第2 observableに移動し、クラッシュしません。しかし、これは問題の解決策ではありません。助けを事前に

EDIT 2

ApiManager.login(userName, pass, new Observer<User>() { 
    @Override 
    public void onCompleted() { } 

    @Override 
    public void onError(Throwable e) { 
     DialogManager.showBasicErrorDialog(getApplicationContext(), e.getLocalizedMessage()); 
     logger.showLog("Login Not ok"); 
     e.printStackTrace(); 
    } 

    @Override 
    public void onNext(User user) { 
     logger.showLog("login ok, user: " + user.getName().toString()); 
     {...} 
    } 

}); 

EDIT 3

FATAL EXCEPTION: main 
rx.exceptions.OnErrorFailedException: Error occurred when trying to propagate error to Observer.onError 
     at rx.observers.SafeSubscriber._onError(SafeSubscriber.java:175) 
     at rx.observers.SafeSubscriber.onError(SafeSubscriber.java:97) 
     at rx.internal.operators.NotificationLite.accept(NotificationLite.java:144) 

{...}

Caused by: java.lang.NullPointerException: Attempt to read from field 'rx.functions.Action0 rx.schedulers.TrampolineScheduler$TimedAction.action' on a null object reference 
     at rx.schedulers.TrampolineScheduler$InnerCurrentThreadScheduler.enqueue(TrampolineScheduler.java:85) 

おかげ。

+0

?コーリングコードはどのように見えますか(オブザーバーの定義)? –

+0

これは編集されていますが、実際にはエラーが目的であるため実際にはあまり関係がありません。 ... –

+0

上記の出力はアプリのクラッシュではありません - それは[エラーをロギングするRetrofit]です(https://github.com/square/retrofit/blob/2c1c6ec370f88e21ac219d8f343f1f6d904c1c87/retrofit/src/main/java/retrofit/RestAdapter.java #L495)。あなたはlogcatフィルタを有効にしていますか?... –

答えて

0

あなたが問題に実行されてようですRxJava 1.0のように固定されているになります。あなたは、スタックトレース/ logcat出力を投稿できる

TrampolineScheduler NullPointerException

+1

私はrxjavaのアンドロイドモジュールを使用しています。今度はjCenterの最新バージョンは0.20.7 です。依存関係:compile 'com.netflix.rxjava:rxjava-android:0.20.7' –

+1

新しいバージョンの[RxAndroid](https:// gitub.com/ReactiveX/RxAndroid)には、 'io.reactivex:rxandroid:0.24.0'というコンパイラの識別子があります。 RxJavaコアモジュールも1.0にアップグレードする必要があります。 –

+0

これは私が考える問題です。 @AdamS何を意味するのか分かりません。「RxJavaコアモジュールを1.0にアップグレードする必要があります。」ところであなたの答えに感謝します。 –

3

あなたはレトロフィットが直接観測返すことができるよう、レトロフィットを使用して独自の観測を構築する必要はありません。

http://square.github.io/retrofit/

レトロフィットもRXの戻り値の型 持つメソッドをサポートするためにRxJavaを統合しています。Observable getUserPhoto(@Path( "id") int id); Observable getUserPhoto(@Path( "id");)

(あなたが自分でエラーを処理する必要はありません)

あなたのクラッシュのスタックトレースを投稿することができますか?私はあなたのように、あなたのアプリケーションはクラッシュするべきではないと思います。

+1

ありがとう、私はあなたのアドバイスのように、コードを修正しました、私のObservableをすべて切り捨てて、変更しました: Observable getUser @Field( "username")文字列userName、@Field( "password")文字列パスワード); しかし、問題は引き続き発生します。エラーは処理されず、アプリケーションがクラッシュします。私はレトロフィットの問題ではなく、RXだと思う。 スタックトレースを追加しました。 –

+0

ところで、Observableに処理する前にオブジェクトで何かしたいのですが? - >ここでは、ログイン時に(ユーザー名、パス) - >ユーザーのオブジェクトに「資格情報」を保存したいのですが、アプリケーション内のすべてのログイン場所ではなく、一度だけ書くとよいです。ここでObservableは何かが起こったことをLoginScreenに伝える前にスーパーファンクションのように動作します。 –

関連する問題

 関連する問題