Java Apache Beam-无法使用hadoop文件系统sdk从S3读取文本文件

Java Apache Beam-无法使用hadoop文件系统sdk从S3读取文本文件,java,hadoop,amazon-s3,apache-beam,apache-beam-io,Java,Hadoop,Amazon S3,Apache Beam,Apache Beam Io,我正在尝试使用beam SDK java io hadoop文件系统v2.0.0和Spark作为运行程序,在beam应用程序中读取AWS EMR集群中的S3。我可以在纱线日志中看到,管道能够检测到S3中存在的文件,但无法读取该文件。请参阅下面的日志 17/06/27 03:29:25 INFO FileBasedSource: Filepattern s3a://xxx/test-folder/* matched 1 files with total size 3410584 17/06/27

我正在尝试使用beam SDK java io hadoop文件系统v2.0.0和Spark作为运行程序,在beam应用程序中读取AWS EMR集群中的S3。我可以在纱线日志中看到,管道能够检测到S3中存在的文件,但无法读取该文件。请参阅下面的日志

17/06/27 03:29:25 INFO FileBasedSource: Filepattern s3a://xxx/test-folder/* matched 1 files with total size 3410584
17/06/27 03:29:25 INFO FileBasedSource: Matched 1 files for pattern s3a://xxx/test-folder/*
17/06/27 03:29:25 INFO FileBasedSource: Splitting filepattern s3a://xxx/test-folder/* into bundles of size 1705292 took 82 ms and produced 1 files and 1 bundles
17/06/27 03:29:25 INFO SparkContext: Starting job: foreach at BoundedDataset.java:109

17/06/27 03:29:33信息块管理信息:在中添加了广播 ip-10-130-237-237上的内存。专有网络。内部:40063(大小:4.6 KB,可用空间: 3.5 GB) 17/06/27 03:29:36警告TaskSetManager:在阶段0.0中丢失任务0.0(TID 0,ip-10-130-237-237.vpc.internal):java.lang.RuntimeException: 无法读取数据。 位于org.apache.beam.runners.spark.io.SourceRDD$Bounded$ReaderToIteratorAdapter.tryProduceNext(SourceRDD.java:198) 在org.apache.beam.runners.spark.io.SourceRDD$Bounded$ReaderToIteratorAdapter.hasNext(SourceRDD.java:239) 位于scala.collection.convert.Wrappers$JIteratorWrapper.hasNext(Wrappers.scala:41) 在org.apache.spark.interruptblediator.hasNext(interruptblediator.scala:39) 在org.apache.spark.storage.MemoryStore.UnrollSafety上(MemoryStore.scala:284) 位于org.apache.spark.CacheManager.putInBlockManager(CacheManager.scala:171) 位于org.apache.spark.CacheManager.getOrCompute(CacheManager.scala:78) 位于org.apache.spark.rdd.rdd.iterator(rdd.scala:268) 在org.apache.spark.rdd.MapPartitionsRDD.compute上(MapPartitionsRDD.scala:38) 在org.apache.spark.rdd.rdd.computeOrReadCheckpoint(rdd.scala:306)上 位于org.apache.spark.rdd.rdd.iterator(rdd.scala:270) 在org.apache.spark.rdd.MapPartitionsRDD.compute上(MapPartitionsRDD.scala:38) 在org.apache.spark.rdd.rdd.computeOrReadCheckpoint(rdd.scala:306)上 位于org.apache.spark.rdd.rdd.iterator(rdd.scala:270) 在org.apache.spark.rdd.MapPartitionsRDD.compute上(MapPartitionsRDD.scala:38) 在org.apache.spark.rdd.rdd.computeOrReadCheckpoint(rdd.scala:306)上 位于org.apache.spark.rdd.rdd.iterator(rdd.scala:270) 位于org.apache.spark.scheduler.ResultTask.runTask(ResultTask.scala:66) 位于org.apache.spark.scheduler.Task.run(Task.scala:89) 位于org.apache.spark.executor.executor$TaskRunner.run(executor.scala:227) 位于java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145) 位于java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615) 运行(Thread.java:745) 原因:java.lang.UnsupportedOperationException:输入流不支持字节缓冲区读取 位于org.apache.hadoop.fs.FSDataInputStream.read(FSDataInputStream.java:146) 位于org.apache.beam.sdk.io.hdfs.HadoopFileSystem$hadoopseekablebytechnel.read(HadoopFileSystem.java:185) 位于org.apache.beam.sdk.io.CompressedSource$CompressedDreader$CountingChannel.read(CompressedSource.java:509) 位于sun.nio.ch.ChannelInputStream.read(ChannelInputStream.java:65) 位于sun.nio.ch.ChannelInputStream.read(ChannelInputStream.java:109) 位于sun.nio.ch.ChannelInputStream.read(ChannelInputStream.java:103) 在java.io.FilterInputStream.read(FilterInputStream.java:133)中 在java.io.PushbackInputStream.read处(PushbackInputStream.java:186) 位于org.apache.beam.sdk.repackaged.com.google.common.io.ByteStreams.read(ByteStreams.java:859) 位于org.apache.beam.sdk.io.CompressedSource$CompressionMode$1.createDecompressingChannel(CompressedSource.java:127) 在org.apache.beam.sdk.io.CompressedSource$decompressionAccordinationofileName.createDecompressingChannel(CompressedSource.java:258) 位于org.apache.beam.sdk.io.CompressedSource$compressedDreader.startReading(CompressedSource.java:542) 位于org.apache.beam.sdk.io.FileBasedSource$FileBasedDrader.startImpl(FileBasedSource.java:471) 在org.apache.beam.sdk.io.OffsetBasedSource$OffsetBasedReader.start(OffsetBasedSource.java:271)上 位于org.apache.beam.runners.spark.io.SourceRDD$Bounded$ReaderToIteratorAdapter.seekNext(SourceRDD.java:214) 位于org.apache.beam.runners.spark.io.SourceRDD$Bounded$ReaderToIteratorAdapter.tryProduceNext(SourceRDD.java:188) ... 还有22个

当我使用
HDFS
作为输入文件系统运行相同的代码时,它工作得非常好。有人能帮我弄清楚如何从S3读取数据吗?输入格式为带有gzip压缩的文本文件

代码:

使用S3运行:

--hdfsConfiguration='[{"fs.default.name": "s3a://xxx/test-folder/*"}]
使用HDFS运行:

--hdfsConfiguration='[{"fs.default.name": "hdfs://xxx/test-folder/*"}]

日志显示输入流不支持读取
字节缓冲区

看起来beam在输入流中需要一个API扩展,而该扩展实际上并没有在S3客户端中实现,所以失败了。这一特性甚至不在Hadoop的未发布版本中,尽管JIRA是最近添加的

没有人会马上动手实现该功能,因为(a)还有更重要的事情要做,(b)这是一个次要的性能优化(内存效率),实际上没有被任何重要的东西使用。您也无法在本地文件系统或Azure中获得它

修正:

  • 通过测试实现Hadoop特性。我保证会帮你复习的
  • 说服别人为你做这件事。对于我们专业的hadoop开发人员来说,这通常发生在重要的人需要它时,无论他们是管理层还是客户
  • 让Beam处理不支持该功能的文件系统&抛出
    不支持操作异常
    ,返回到
    读取(字节[])
    。这就是他们所要做的
  • 变通办法

    • 以不同的压缩格式存储数据
    • 首先将其复制到HDFS
    我建议您首先在BEAM下查找错误/堆栈跟踪,然后在不存在错误/堆栈跟踪的情况下提交新报告。看看他们怎么说


    更新:关注

    谢谢你,史蒂夫。我们将评估并决定从这里走哪条路。
    --hdfsConfiguration='[{"fs.default.name": "hdfs://xxx/test-folder/*"}]