Android.os.NetworkOnMainThreadException usando rxjava en android

Estoy teniendo problemas para implementar rxJava con el fin de comprobar si hay conexión a Internet en android lo estoy haciendo así:

En mi actividad del lanzador tengo esto en onCreate:

AndroidObservable.bindActivity(this, Observable.just(Utils.isActiveInternetConnection(Launcher.this))) .subscribeOn(Schedulers.newThread()) .subscribe(new Action1<Boolean>() { @Override public void call(Boolean aBoolean) { if (aBoolean) { Toast.makeText(Launcher.this, "There is internet connection", Toast.LENGTH_SHORT).show(); } else { Toast.makeText(Launcher.this, "There is no internet connection", Toast.LENGTH_SHORT).show(); } } }); 

Tengo una clase Utils es una clase final con métodos estáticos los métodos en los que el observable está usando son los siguientes:

  public static boolean isActiveInternetConnection(Context context) { if (isNetworkAvailable(context)) { try { HttpURLConnection urlc = (HttpURLConnection) (new URL("http://www.google.com").openConnection()); urlc.setRequestProperty("User-Agent", "Test"); urlc.setRequestProperty("Connection", "close"); urlc.setConnectTimeout(1500); urlc.connect(); return (urlc.getResponseCode() == 200); } catch (IOException e) { Log.e("network", "Error checking internet connection", e); } } else { Log.d("network", "No network available!"); } return false; } private static boolean isNetworkAvailable(Context context){ ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); NetworkInfo activeNetwork = cm.getActiveNetworkInfo(); if (null != activeNetwork) { return true; } else { return false; } } 

Estoy recibiendo android.os.NetworkOnMainThreadException y no puedo encontrar por qué, gracias de antemano.

Observable.just(...) se llama inmediatamente en el hilo llamante (el hilo principal, en este caso). Su código es efectivamente sólo una versión en línea de este:

 boolean activeConn = Utils.isActiveInternetConnection(Launcher.this); AndroidObservable.bindActivity(this, Observable.just(activeConn)) .subscribeOn(...) ... 

Has intentado moverlo fuera del hilo principal llamando a subscribeOn() – pero la llamada ya ha ocurrido.

La forma en que manejamos esto (y no estoy seguro de que sea la mejor manera, pero funciona) es aplazar la red o bloquear la llamada hasta que suceda la suscripción, configurar el observable para ejecutar en los hilos correctos y luego suscribirse:

 AndroidObservable.bindActivity(this, Observable.defer(new Func0<Boolean>() { @Override public Observable<Observable<Boolean>> call() { return Observable.just(Utils.isActiveInternetConnection(Launcher.this)); } }) .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(new Action1<Boolean>() { @Override public void call(Boolean aBoolean) { if (aBoolean) { Toast.makeText(Launcher.this, "There is internet connection", Toast.LENGTH_SHORT).show(); } else { Toast.makeText(Launcher.this, "There is no internet connection", Toast.LENGTH_SHORT).show(); } } }); 

Supongo que just llama al método de forma síncrona, ya que espera el valor booleano y trata de obtenerlo.

Soy algo malo en RxJava pero usted puede intentar algo como esto:

 Observable<Boolean> onlineObservable = Observable.create(new Observable.OnSubscribe<Boolean>() { @Override public void call(Subscriber subscriber) { subscriber.onNext(Utils.isActiveInternetConnection(context)); } }); onlineObservable.subscribeOn(Schedulers.newThread()).subscribe(result -> {...}); 

Este es mi recuperar datos de DataBase por RXAndroid código:

  Observable.create(new Observable.OnSubscribe<List<GRO_VO>>() { @Override public void call(Subscriber<? super List<GRO_VO>> subscriber) { String jsonIn; jsonIn =retrieveDataFromDB(); Gson gson = new Gson(); Type listType = new TypeToken<List<GRO_VO>>() { }.getType(); eventJoinList = gson.fromJson(jsonIn, listType); Log.d("RX",jsonIn); subscriber.onNext(eventJoinList); } }) .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(new Action1<List<GRO_VO>>() { @Override public void call(List<GRO_VO> eventJoinList) { Log.d("RX", ".subscribe"); recyclerView.setAdapter(new EventJoinAdapter(eventJoinList)); } }); 

Creo que el operador just emitir datos inmediatamente, por lo que no es útil para recuperar los datos de una base de datos a través de la red. Es muy fácil de usar, pero sólo puede utilizarse para datos que ya están en el móvil.

También tuve ese problema, como @Baniares, pero después de usar el operador create , el problema desaparece …

De la documentación de RXJava:

static <T> Observable<T> create(Observable.OnSubscribe<T> f)

Devuelve un Observable que ejecutará la función especificada cuando un Suscriptor se suscriba a ella.

El uso del operador create puede establecer el proceso estándar:

1 .subscribe(...) Subscriber (la subclase de la clase Observer) inicia la conexión a Observable.

2 .subscribeOn(Schedulers.io()) recopila un hilo de backGround desde el RX-ThreadPool

3 .create(...) recuperar datos del servidor … durante algún netWork..etc

4 .observeOn(AndroidSchedulers.mainThread()) esto significa que los datos serán establecidos por el UI-Thread

5 Una vez que obtengamos los datos, podemos configurar los datos en el método onNext () en .subscribe( ) , los datos se establecerán en la interfaz de usuario por UI-Thread ya que hacemos el hilo de interfaz de usuario hacer el trabajo en el .observerOn(AndroidSchedulers.mainThread())

La cadena de métodos simplemente no ocurre por el orden en el código.

Y tenga en cuenta que si utiliza el operador .create (), debe haber terminado su observable en el .create (), otros operadores como map, flatMap no se ejecutará después del operador .create ().

AdamS es correcto, sin embargo RxJava 2 ahora ofrece Observable.fromCallable () para diferir una operación observable hasta la suscripción. Una buena referencia: https://caster.io/lessons/fromcallable-converting-slow-methods-into-an-observable/

Algunos ejemplos de código de mi caso de uso:

 Single.fromCallable(new Callable<Response>() { @Override public Response call() throws Exception { return NetworkGateway.networkRequest(); } }) .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer); 

Su método isActiveInternetConnection tratando de conectarse a la red desde el hilo principal de la aplicación, trate de utilizar handler o asynctask para este método Más información sobre el error: ¿Cómo arreglar android.os.NetworkOnMainThreadException?

  • AbstractMethodError cuando se utiliza RxJavaCallAdapterFactory en Retrofit 2
  • Manejo de listas con RxJava y Retrofit en android
  • ¿Existe algún patrón de desarrollo que pueda reemplazar un IntentService para las solicitudes de red?
  • Prueba de unidad de presentador con RxJava CompositeSubscription
  • RxAndroid, bus de eventos y ciclo de vida de la actividad
  • Kotlin: ¿Qué significa "return @"?
  • ¿Hay RxJava equivalente a Handler.postDelayed (Runnable r, delayMillis largo)
  • Solicitudes HTTP periódicas con RxJava y Retrofit
  • Solución global de errorHandling con RxJava sólo cuando onError no está implementado
  • Añadir RxJava Observer en cadena dependiendo de una condición
  • Por qué definir Flowable podría recibir actualizaciones de la base de datos
  • FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.