Node.js 如何解析节点中的大型分隔文本文件

Node.js 如何解析节点中的大型分隔文本文件,node.js,logging,stream,gzip,pipe,Node.js,Logging,Stream,Gzip,Pipe,我使用Node来处理来自应用程序的日志文件,由于通信量的原因,这些日志文件每天的大小可能是1 GB左右 这些文件每天晚上都会被抓取,我需要阅读这些文件,而不必将它们解压缩到磁盘上 据我所知,我可以使用zlib将文件解压缩为某种形式的流,但我不知道如何获取数据,也不知道如何一次轻松处理一行(尽管我知道会涉及某种while循环搜索) 到目前为止,我找到的最接近的答案是演示如何将流输送到sax解析器,但是整个节点管道/流有点混乱 fs.createReadStream('large.xml.gz').

我使用Node来处理来自应用程序的日志文件,由于通信量的原因,这些日志文件每天的大小可能是1 GB左右

这些文件每天晚上都会被抓取,我需要阅读这些文件,而不必将它们解压缩到磁盘上

据我所知,我可以使用zlib将文件解压缩为某种形式的流,但我不知道如何获取数据,也不知道如何一次轻松处理一行(尽管我知道会涉及某种while循环搜索)

到目前为止,我找到的最接近的答案是演示如何将流输送到sax解析器,但是整个节点管道/流有点混乱

fs.createReadStream('large.xml.gz').pipe(zlib.createUnzip()).pipe(saxStream);
你应该看一看。 它是由艾萨克开发的

我还没有测试过这段代码,但我会从写这些代码开始

var Promise = Promise || require('es6-promise').Promise
, thr = require('through2')
, createReadStream = require('fs').createReadStream
, createUnzip = require('zlib').createUnzip
, createParser = require('sax').createStream
;

function processXml (filename) {
  return new Promise(function(resolve, reject){
    var unzip = createUnzip()
    , xmlParser = createParser()
    ;

    xmlParser.on('opentag', function(node){
      // do stuff with the node
    })
    xmlParser.on('attribute', function(node){
      // do more stuff with attr 
    })

    // instead of rejecting, you may handle the error instead.
    xmlParser.on('error', reject) 
    xmlParser.on('end', resolve)

    createReadStream(filename)
    .pipe(unzip)
    .pipe(xmlParser)
    .pipe(thr(function(chunk, enc, next){
      // as soon xmlParser is done with a node, it passes down stream.
      // change the chunk if you wish
      next(null, newerChunk)
    }))

    rl = readline.createInterface({
      input: unzip
    , ouput: xmlParser
    })
  })
}

processXml('large.xml.gz').then(function(){
  console.log('done')
})
.catch(function(err){
  // handle error.
})
我希望这对你有所帮助,你应该看看。 它是由艾萨克开发的

我还没有测试过这段代码,但我会从写这些代码开始

var Promise = Promise || require('es6-promise').Promise
, thr = require('through2')
, createReadStream = require('fs').createReadStream
, createUnzip = require('zlib').createUnzip
, createParser = require('sax').createStream
;

function processXml (filename) {
  return new Promise(function(resolve, reject){
    var unzip = createUnzip()
    , xmlParser = createParser()
    ;

    xmlParser.on('opentag', function(node){
      // do stuff with the node
    })
    xmlParser.on('attribute', function(node){
      // do more stuff with attr 
    })

    // instead of rejecting, you may handle the error instead.
    xmlParser.on('error', reject) 
    xmlParser.on('end', resolve)

    createReadStream(filename)
    .pipe(unzip)
    .pipe(xmlParser)
    .pipe(thr(function(chunk, enc, next){
      // as soon xmlParser is done with a node, it passes down stream.
      // change the chunk if you wish
      next(null, newerChunk)
    }))

    rl = readline.createInterface({
      input: unzip
    , ouput: xmlParser
    })
  })
}

processXml('large.xml.gz').then(function(){
  console.log('done')
})
.catch(function(err){
  // handle error.
})

我希望帮助

你是否考虑过编写一个本地扩展并使用C++库?如果你的文件很大,这可能是最好的选择…不知道C++ + TBH。现在我可以通过解压缩文件然后使用期限来完成,但是当我把它滚入生产环境时,权限被锁定,所以我不能继续。E日志文件夹的内容,只从它读取。尝试用SUDO执行节点进程。您可以在这里逐行解析文件。虽然您必须通过解压缩流。但是,运行一个服务并不是一个很好的安全实践,您是否考虑过编写本机扩展和使用C++库?如果您的文件是LUG的话。现在,我可以通过解压缩文件然后使用期限来完成,但是当我把它放到生产环境中时,权限被锁定,所以我不能更改日志文件夹的内容,只从C++中读取。尝试用SUDO执行节点进程。可以在这里看到。不过,您必须通过解压缩流。要像sudo一样运行服务,这并不是一个好的安全实践