2016-11-03 3 views
3

함께 축삭을 약속하고 업로드 진행 상황을 사용하여 깨끗한/짧은/오른쪽 방법 있나요? 이 기능은 약속을 반환Redux Saga, Axios 및 progress 이벤트

function upload(payload, onProgress) { 
    const url = '/sources/upload'; 

    const data = new FormData(); 

    data.append('source', payload.file, payload.file.name); 

    const config = { 
    onUploadProgress: onProgress, 
    withCredentials: true 
    }; 

    return axios.post(url, data, config); 
} 

:

내가 다음 업로드 기능을 가지고 가정하자.

function* uploadSaga(action) { 
    try { 
    const response = yield call(upload, payload, [?? anyProgressFunction ??]); 
    yield put({ type: UPLOADING_SUCCESS, payload: response }); 
    } catch (err) { 
    yield put({ type: UPLOADING_FAIL, payload: err }); 
    } 
} 

내가 진행 이벤트를 수신하고 사가로 넣어 원하는 :

또한 나는 사가있다. 또한 나는 축삭 요청의 성공 (또는 실패) 결과를 잡아 내고 싶다. 가능한가?

감사합니다.

답변

7

답변을 찾았으므로 설명을 위해 Mateusz Burzyński에게 감사드립니다.

eventChannel을 사용해야하지만 약간의 시간이 걸릴 수 있습니다.

생각에는 우리는 업로드 파일에 대한 API 함수를 가지고 : 사가에서

function upload(payload, onProgress) { 
    const url = '/sources/upload'; 

    const data = new FormData(); 

    data.append('source', payload.file, payload.file.name); 

    const config = { 
    onUploadProgress: onProgress, 
    withCredentials: true 
    }; 

    return axios.post(url, data, config); 
} 

우리가 eventChannel을 작성해야하지만 외부에 방출했습니다.

function createUploader(payload) { 

    let emit; 
    const chan = eventEmitter(emitter => { 

    emit = emitter; 
    return() => {}; // it's necessarily. event channel should 
        // return unsubscribe function. In our case 
        // it's empty function 
    }); 

    const uploadPromise = upload(payload, (event) => { 
    if (event.loaded.total === 1) { 
     emit(END); 
    } 

    emit(event.loaded.total); 
    }); 

    return [ uploadPromise, chan ]; 
} 

function* watchOnProgress(chan) { 
    while (true) { 
    const data = yield take(chan); 
    yield put({ type: 'PROGRESS', payload: data }); 
    } 
} 

function* uploadSource(action) { 
    const [ uploadPromise, chan ] = createUploader(action.payload); 
    yield fork(watchOnProgress, chan); 

    try { 
    const result = yield call(() => uploadPromise); 
    put({ type: 'SUCCESS', payload: result }); 
    } catch (err) { 
    put({ type: 'ERROR', payload: err }); 
    } 
} 
+0

대신 eventEmitter가 'eventChannel'이되어야합니까? –