Saltar al contenido

Use fetch en lugar de ajax con redux-observable

Después de consultar con expertos en esta materia, programadores de varias áreas y profesores dimos con la respuesta al problema y la compartimos en este post.

Solución:

(Nota: RX.DOM.ajax es de RxJS v4y no funciona con redux-observable que requiere RxJS v5. El equivalente en v5 es Rx.Observable.ajax o import ajax from 'rxjs/observable/ajax';)

De hecho, es posible utilizar fetch() así como cualquier otra API de AJAX; ¡aunque algunos se adaptan más fácilmente que otros!

Él fetch() La API devuelve un Promiseque tiene RxJS v5 soporte incorporado para. La mayoría de los operadores que esperan un observable pueden consumir Promises tal cual (como mergeMap, switchMap, etc). Pero a menudo querrá aplicar operadores Rx a la Promesa antes de pasarla al resto de su Epic, por lo que a menudo querrá envolver la Promesa dentro de un Observable.

Puedes envolver una Promesa en un Observable con Observable.from(promise)

Aquí hay un ejemplo en el que busco un usuario, solicito la respuesta JSON y luego envuelvo la promesa en un observable:

const api = 
  fetchUser: id => 
    const request = fetch(`https://jsonplaceholder.typicode.com/users/$id`)
      .then(response => response.json());
    return Observable.from(request);
  
;

Luego puede consumir eso en su Epic y aplicar los operadores que desee:

const fetchUserEpic = action$ =>
  action$.ofType(FETCH_USER)
    .mergeMap(action =>
      api.fetchUser(action.payload) // This returns our Observable wrapping the Promise
        .map(payload => ( type: FETCH_USER_FULFILLED, payload ))
    );

Aquí hay un JSBin con este ejemplo de trabajo: https://jsbin.com/fuwaguk/edit?js,output


Si tiene control sobre el código API, idealmente usaría Observable.ajax (o cualquier otra utilidad AJAX basada en Observable) porque las Promesas no se pueden cancelar. (a partir de este escrito)

Hice un pequeño ajuste en @jayphelps para que ese código me funcionara. Espero que esto ayude a ahorrar tiempo a alguien.

import  FETCH_USER  from './actions'
import  ofType  from 'redux-observable'
import  map, mergeMap  from 'rxjs/operators'
import  from  from 'rxjs'

const fetchUserEpic = action$ => 
    return action$.pipe(
        ofType(FETCH_USER),
        mergeMap((action =  user: 'redux-observable' ) => 
            const getRequest = (user) => 
                const request = fetch(`https://api.github.com/users/$user`)
                    .then(response => response.json())
                return from(request)
            

            return getRequest(action.user).pipe(
               map(payload => ( type: FETCH_USER_FULFILLED, payload ))
            )
        )
    )

Si para ti ha sido útil nuestro post, sería de mucha ayuda si lo compartes con más programadores de este modo nos ayudas a dar difusión a nuestro contenido.

¡Haz clic para puntuar esta entrada!
(Votos: 0 Promedio: 0)



Utiliza Nuestro Buscador

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *