2015-11-25 47 views
0

有一个busboy library。对于某些承诺库,我可以用下面的代码收集一个对象的整个表单数据:RxJS和Busboy

var p = new Promise((resolve) => { 
    let res = {} 
    busboy.on('file', (fieldname, file, filename, encoding, mimetype)=> { 
    let name = uuid.v1() 
    let extension = path.extname(filename) 
    let saveTo = path.resolve(mediaPath, `${name}${extension}`) 
    file.pipe(fs.createWriteStream(saveTo)) 
    res = _.extend(res, { 
     [fieldname]: { filename } 
    }) 
    }) 
    busboy.on('field', (key, value, keyTruncated, valueTruncated) => { 
    res = _.extend({[key]: value}) 
    }) 
    busboy.on('finish',() => resolve(res)) 
}) 
p.then((data) => ... 

它的工作原理,但它看起来有点意大利面条一样小。有没有办法用RxJS来改进这个样本?

+0

试试这个http://xgrommx.github.io/rx-book/content/observable/observable_methods/fromevent.html – xgrommx

+0

你建议设立3不同的序列(对于每种类型的事件),合并它们并减少一个对象? – kharandziuk

回答

1

我可以考虑一些使用Rxjs的方法,但我不确定这意味着需要更少的代码。

您可以: - 以与使用Rx.Observable.fromEvent包装DOM事件相同的方式包装您的busboy库事件。

然后做这样的事情:

var fileEvent$ = Rx.Observable.fromBusyBoyEvent('file'); 
var fieldEvent$ = Rx.Observable.fromBusyBoyEvent('field'); 
var finishEvent$ = Rx.Observable.fromBusyBoyEvent('finish'); 
var processFileEvent = function (res, fieldname, file, filename, encoding, mimetype) { 
    /*code here*/ 
    return {res : /* something*/, done : false} 
}; 
var processFieldEvent = function (res, key, value, keyTruncated, valueTruncated) {/*code here*/ 
    return {res : /* something*/, done : false} 
}; 
var processFinishEvent = function (res) {return {res : res, done : true}}; 

var passReducer = function (reduce_fn) { 
    return function() { 
    return {args : arguments, reduce_fn : reduce_fn} 
    } 
}; 

var res$ = Rx.Observable 
    .merge(
    fileEvent$.map(passReducer(processFileEvent)), 
    fieldEvent$.map(passReducer(processFieldEvent)), 
    finishEvent$.map(passReducer(processFinishEvent))) 
    .scan(function (acc, command) { 
      return command.reduce_fn.apply(null, command.args); 
      }, {}) 
    .filter(function (acc) {return acc.done});