Spark 使用 sc.textFile("s3a://bucket/filePath") 读取 s3。 java.lang.NoSuchMethodError:com.amazo

Posted

技术标签:

【中文标题】Spark 使用 sc.textFile("s3a://bucket/filePath") 读取 s3。 java.lang.NoSuchMethodError:com.amazonaws.services.s3.transfer.TransferManager【英文标题】:Spark read s3 using sc.textFile("s3a://bucket/filePath"). java.lang.NoSuchMethodError: com.amazonaws.services.s3.transfer.TransferManager 【发布时间】:2017-05-12 03:53:51 【问题描述】:

我已将自爆罐添加到 spark/jars 路径。

hadoop-aws-2.7.3.jar aws-java-sdk-s3-1.11.126.jar aws-java-sdk-core-1.11.126.jar spark-2.1.0

在 spark-shell 中

scala> sc.hadoopConfiguration.set("fs.s3a.access.key", "***")

scala> sc.hadoopConfiguration.set("fs.s3a.secret.key", "***")

scala> val f = sc.textFile("s3a://bucket/README.md")

scala> f.count

java.lang.NoSuchMethodError: com.amazonaws.services.s3.transfer.TransferManager.(Lcom/amazonaws/services/s3/AmazonS3;Ljava/util/concurrent/ThreadPoolExecutor;)V 在 org.apache.hadoop.fs.s3a.S3AFileSystem.initialize(S3AFileSystem.java:287) 在 org.apache.hadoop.fs.FileSystem.createFileSystem(FileSystem.java:2669) 在 org.apache.hadoop.fs.FileSystem.access$200(FileSystem.java:94) 在 org.apache.hadoop.fs.FileSystem$Cache.getInternal(FileSystem.java:2703) 在 org.apache.hadoop.fs.FileSystem$Cache.get(FileSystem.java:2685) 在 org.apache.hadoop.fs.FileSystem.get(FileSystem.java:373) 在 org.apache.hadoop.fs.Path.getFileSystem(Path.java:295) 在 org.apache.hadoop.mapred.FileInputFormat.singleThreadedListStatus(FileInputFormat.java:258) 在 org.apache.hadoop.mapred.FileInputFormat.listStatus(FileInputFormat.java:229) 在 org.apache.hadoop.mapred.FileInputFormat.getSplits(FileInputFormat.java:315) 在 org.apache.spark.rdd.HadoopRDD.getPartitions(HadoopRDD.scala:202) 在 org.apache.spark.rdd.RDD$$anonfun$partitions$2.apply(RDD.scala:252) 在 org.apache.spark.rdd.RDD$$anonfun$partitions$2.apply(RDD.scala:250) 在 scala.Option.getOrElse(Option.scala:121) 在 org.apache.spark.rdd.RDD.partitions(RDD.scala:250) 在 org.apache.spark.rdd.MapPartitionsRDD.getPartitions(MapPartitionsRDD.scala:35) 在 org.apache.spark.rdd.RDD$$anonfun$partitions$2.apply(RDD.scala:252) 在 org.apache.spark.rdd.RDD$$anonfun$partitions$2.apply(RDD.scala:250) 在 scala.Option.getOrElse(Option.scala:121) 在 org.apache.spark.rdd.RDD.partitions(RDD.scala:250) 在 org.apache.spark.SparkContext.runJob(SparkContext.scala:1958) 在 org.apache.spark.rdd.RDD.count(RDD.scala:1157) ... 48 省略

    “java.lang.NoSuchMethodError: com.amazonaws.services.s3.transfer.TransferManager”由不匹配的 jar 引发? (hadoop-aws, aws-java-sdk)

    要从 Spark 应用程序访问存储在 Amazon S3 中的数据,应使用 Hadoop 文件 API。那么 hadoop-aws.jar 是包含 Hadoop 文件 APIS 还是必须运行 hadoop env ?

【问题讨论】:

【参考方案1】:

不匹配的 JAR; AWS 开发工具包跨版本非常脆弱。

Hadoop S3A 代码在 hadoop-aws JAR 中;还需要hadoop-common。 Hadoop 2.7 是针对 AWS S3 SDK 1.10.6 构建的。 (*更新:不,它是 1.7.4。迁移到 1.10.6 进入 Hadoop 2.8)HADOOP-12269

您必须使用该版本。如果您想使用 1.11 JAR,那么您需要查看 hadoop 源代码树并自己构建 branch-2。好消息:它使用带阴影的 AWS 开发工具包,因此它的 jackson 和 joda time 版本不会破坏任何东西。哦,如果您查看 spark master,并使用 -Phadoop-cloud 配置文件进行构建,它会提取正确的内容以正确设置 Spark 的依赖项。

更新:2017 年 10 月 1 日:Hadoop 2.9.0-alpha 和 3.0-beta-1 使用 1.11.199;假设发货版本将是该版本或更新版本。

【讨论】:

"Hadoop S3A 代码在 hadoop-aws JAR 中;还需要 hadoop-common。Hadoop 2.7 是针对 AWS S3 SDK 1.10.6 构建的。"最终用户如何自己弄清楚这样的细节?我遇到了与hadoop-aws:2.7.4 的 OP 类似的错误,我不确定我需要将哪些内容和版本传递给spark-submit 以使s3a:// 按预期工作。我尝试了几个版本的aws-java-sdk 都没有成功。 我尝试在here 中寻找线索,但没有版本说明。我不熟悉 Java 开发,所以也许我错过了在哪里看。 哦,你离得太近了。在一个大型 maven 项目中,您在一个文件中定义事物的版本(以及您不想要的 cruft),然后引用它们。给你github.com/apache/hadoop/blob/release-2.7.4-RC0/hadoop-project/… - 1.7.4 啊,好的!越来越近了,但我想还有一个缺失的部分。我将hadoop-aws:2.7.4 传递给spark-submit --packages。有了它,我可以在 S3 上读取单部分 ORC 数据集,但不能读取多部分 Parquet 数据集。多部分数据集给出了NoSuchMethodError: TransferManager 错误。如果我将aws-java-sdk:1.7.4 添加到我的--packages 列表中,它似乎没有帮助。我在多部分数据集上遇到了同样的错误。通过 Hadoop 存储库,我没有看到该 POM 文件中提到的任何其他与 AWS 相关的依赖项。 我认为我的问题与 EMR/YARN 有关。如果我从我的spark-submit 调用中删除--master yarn,我可以只用--packages hadoop-aws:2.7.4 做我需要做的所有事情。我想我应该把这个带到 EMR 论坛。目前正在使用 s3a://、一个 EMR 集群和一个远程 EC2 Spark 客户端。

以上是关于Spark 使用 sc.textFile("s3a://bucket/filePath") 读取 s3。 java.lang.NoSuchMethodError:com.amazo的主要内容,如果未能解决你的问题,请参考以下文章

Spark 使用 sc.textFile("s3a://bucket/filePath") 读取 s3。 java.lang.NoSuchMethodError:com.amazo

使用 sc.textFile() 加载本地文件以触发

Spark RDD 操作实战之文件读取

spark配置

Spark运行流程

Spark:sc.textFiles() 与 sc.wholeTextFiles() 的区别