Réponses:
Comme @markerikson le dit déjà, redux-saga
expose une API très utile select()
pour invoquer un selector
état pour en obtenir une partie disponible dans la saga.
Pour votre exemple, une implémentation simple pourrait être:
/*
* Selector. The query depends by the state shape
*/
export const getProject = (state) => state.project
// Saga
export function* saveProjectTask() {
while(true) {
yield take(SAVE_PROJECT);
let project = yield select(getProject); // <-- get the project
yield call(fetch, '/api/project', { body: project, method: 'PUT' });
yield put({type: SAVE_PROJECT_SUCCESS});
}
}
En plus de la doc suggérée par @markerikson, il y a un très bon tutoriel vidéo de D. Abramov qui explique comment l'utiliser selectors
avec Redux. Consultez également ce fil intéressant sur Twitter.
C'est à cela que servent les fonctions "sélecteur". Vous leur passez l'arbre d'état entier, et ils renvoient une partie de l'état. Le code qui appelle le sélecteur n'a pas besoin de savoir où dans l'état où se trouvaient les données, mais simplement qu'elles ont été renvoyées. Voir http://redux.js.org/docs/recipes/ComputingDerivedData.html pour quelques exemples.
Dans une saga, l' select()
API peut être utilisée pour exécuter un sélecteur.
J'ai utilisé un eventChannel pour envoyer une action à partir d'un rappel dans la fonction générateur
import {eventChannel} from 'redux-saga';
import {call, take} from 'redux-saga/effects';
function createEventChannel(setEmitter) {
return eventChannel(emitter => {
setEmitter(emitter)
return () => {
}
}
)
}
function* YourSaga(){
let emitter;
const internalEvents = yield call(createEventChannel, em => emitter = em)
const scopedCallback = () => {
emitter({type, payload})
}
while(true){
const action = yield take(internalEvents)
yield put(action)
}
}