为什么没有传奇功能接受第二次请求?

时间:2016-08-26 19:06:21

标签: javascript asynchronous async-await redux redux-saga

所以我猜我在做一些根本错误的事情。当我第一次从浏览器上传图像时,下面的函数会触发但只发生一次。所以下次我上传一张图片时,我看不到再次运行watchFileReader函数..这很奇怪,它正在发生...因为我正在获得其他传奇函数以按预期运行! 有人能告诉我我可能做错了什么吗?

export function* watchFileReader() {
  const action = yield take("DROP_FILE")
  console.log('action', action)
  let file = action.file[0];
  readFile(file, function(e) {
    sessionStorage.removeItem('img')
    console.log('alskdjfalsdjkf', e.target.result)
    sessionStorage.setItem('img', e.target.result)
  })
}

export const readFile = (file, callback) => {
  let reader = new FileReader()
  reader.onloadend = callback;
  reader.readAsDataURL(file)
}

export function* rootSaga() {
  yield [
    watchFileReader()
  ]
}

2 个答案:

答案 0 :(得分:1)

take效果只会产生一次。您可以将观察者代码粘贴到while循环中,也可以使用redux-saga中的takeEvery帮助程序。

因为它是一个生成器函数,所以saga被暂停,直到动作被中间件捕获并再次产生,所以它不像你在后台占用cpu时会有一堆无限循环。

我使用与许多文档相同的设计模式,即拥有一个观察者'在循环上运行的saga /进程,用于执行每个分派的操作,以及一个工作者传奇或进程的火灾,从而实现真正繁重的工作。

TakeEvery(或者如果你只想要获取最新的一个,则最小化)就像一个永远运行的while循环,每次它获取它所寻找的动作时,都会分叉一个新的worker,这使它成为一个非阻塞操作。

export function* fileReaderWorker(action) {
  console.log('action', action)
  let file = action.file[0];
  readFile(file, function(e) {
    sessionStorage.removeItem('img')
    console.log('alskdjfalsdjkf', e.target.result)
    sessionStorage.setItem('img', e.target.result)
  })
}

export function* watchFileReader() {
  yield takeEvery("DROP_FILE", fileReaderWorker)
}
// or the loop version
// while (true) {
//  const action = yield take("DROP_FILE")
//  yield fork(fileReaderWorker, ...args.concat(action))
//}

export const readFile = (file, callback) => {
  let reader = new FileReader()
  reader.onloadend = callback;
  reader.readAsDataURL(file)
}

export function* rootSaga() {
  yield [
    watchFileReader()
  ]
}

答案 1 :(得分:0)

删除第一个文件后,saga生成器function的状态将被暂停,即{done: false}。要将状态保持为有效状态,您可以将收益率function包装在infinite while loop

export function* watchFileReader() {
  while(true) {
   const action = yield take("DROP_FILE")
   console.log('action', action)
   let file = action.file[0];
   readFile(file, function(e) {
    sessionStorage.removeItem('img')
    console.log('alskdjfalsdjkf', e.target.result)
    sessionStorage.setItem('img', e.target.result)
  })
 }
}

或使用redux-saga提供的takeEvery或takeLatest副作用。