AKKA FileIO Stream解析到Newline& EOF

时间:2017-05-15 17:09:20

标签: scala parsing akka newline eof

我正在使用Akka FileIO(在scala中)创建一个文件解析器,用于从输入文件中读取每一行并应用一个简单的接收器。除了文件中以EOF结尾的最后一行外,每一行都用换行符(' \ n')分隔。

我如何处理换行和自由分隔,这样我才能可靠地读取最后一行,而不必依赖最终的' / n'字符?

    var rowNum = 0
    val simpleMsgSink: Sink[String, Future[Done]] =
      Sink.foreach {
        case row: String => {
          println(s"$rowNum: $row")
          rowNum = rowNum+1
        }
      }
    val source = FileIO.fromPath(file, 1 * 1024 * 1024 )
      .via(Framing.delimiter(ByteString("\n"), maximumFrameLength = 1024))
      .map(_.utf8String)
      .runWith(simpleMsgSink)

如果对文件执行此操作(最后一行末尾没有换行符):

Sensor_ID,Location,Seqno,gwrx.time,Temp,Humidity,Noise,CO2,Water
A0890,"51.645368, 0.072211",1,42793.00278,16,48,36,325,0
A0891,"51.645370, 0.072300",1,42793.00278,15,41,34,353,3

输出结果为:

0: Sensor_ID,Location,Seqno,gwrx.time,Temp,Humidity,Noise,CO2,Water
1: A0890,"51.645368, 0.072211",1,42793.00278,16,48,36,325,0

如何拾取最后一行?

1 个答案:

答案 0 :(得分:0)

如果您查看Framing.delimiter的{​​{3}},您会看到它实际上有第三个参数:allowTruncation,默认值为false。这就是scaladoc所说的:

  

如果是false,那么当被解码的最后一帧不包含有效的分隔符时,此流将使流失败而不是返回截断的帧。

所以你需要做的就是添加缺少的参数:

Framing.delimiter(ByteString("\n"), maximumFrameLength = 1024, allowTruncation = true)