Skip to content

Instantly share code, notes, and snippets.

@ThisIsMissEm
Created February 25, 2017 20:16
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ThisIsMissEm/7e6df63ee448c2edfb56d378d67d8d30 to your computer and use it in GitHub Desktop.
Save ThisIsMissEm/7e6df63ee448c2edfb56d378d67d8d30 to your computer and use it in GitHub Desktop.

Concept:

When a user logs in, we want to fetch their settings and propagate them into the Redux store; However, the request for fetching the settings can take some time (we're primarily operating on mobile networks), so there's a chance that whilst we're waiting for the users settings to come back from the backend that the user may have already logged out. As such, we don't want to apply the settings to the store, as that would result in incorrect state.

import { put, takeEvery, call } from 'redux-saga/effects'
import backend from '@ada/lib/Backend'
import settings from '@ada/redux/modules2/settings'
export function* reloadSettings () {
const newSettings = yield call(backend.fetchAuth, 'user/settings')
yield put(settings.actions.replace(newSettings))
}
export function* watchAuthentication() {
// This saga is loosely based on the saga used in takeLatest(pattern, callback),
// which forks the callback, and cancels it if another value comes through
// on take(pattern)
let lastTask
while (true) {
const {authenticated, unauthenticated } = yield race({
authenticated: take(authentication.types.authenticated),
unauthenticated: take(authentication.types.unauthenticated)
})
if (lastTask) {
yield cancel(lastTask) // cancel is no-op if the task has already terminated
}
if (authenticated) {
// This forks off into the background, meaning that if we get an unauthenticated
// request in the mean time whilst we wait for the backend request to resolve,
// then we cancel that request, hence, when it does resolve we don't get settings
// for the now unauthenticated account
lastTask = yield fork(reloadSettings)
} else {
yield put(settings.actions.clear())
lastTask = undefined
}
}
}
export default function* rootSaga() {
yield fork(watchAuthentication)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment