【问题标题】:Spark in AWS: "S3AbortableInputStream: Not all bytes were read from the S3ObjectInputStream"AWS 中的 Spark:“S3AbortableInputStream:并非所有字节都从 S3ObjectInputStream 中读取”
【发布时间】:2018-06-20 03:16:24
【问题描述】:

我正在运行 PySpark 应用程序:

  • emr-5.8.0
  • Hadoop 发行版:Amazon 2.7.3
  • Spark 2.2.0

我在一个非常大的集群上运行。该应用程序从 s3 读取一些输入文件。其中之一被加载到内存中并广播到所有节点。另一个使用 SparkFiles 功能分发到集群中每个节点的磁盘。该应用程序可以工作,但性能比大型作业的预期慢。查看日志文件,我看到以下警告几乎不断重复:

WARN S3AbortableInputStream: Not all bytes were read from the S3ObjectInputStream, aborting HTTP connection. This is likely an error and may result in sub-optimal behavior. Request only the bytes you need via a ranged GET or drain the input stream after use.

这往往发生在有关访问已加载到内存并广播的文件的消息之后。这个警告是要警告的吗?如何避免?

Google 搜索显示了几个人在本地 Hadoop 应用程序中处理此警告,但我在 Spark 或 PySpark 中没有发现任何相关信息,并且无法弄清楚这些解决方案将如何适用于我。

谢谢!

【问题讨论】:

    标签: hadoop apache-spark pyspark hdfs


    【解决方案1】:

    忽略它。 当您在输入流上调用 abort() 时,AWS 开发工具包的更新版本总是会告诉您,即使您在移动许多 GB 文件时需要这样做。对于小文件,是的,读取 EOF 是正确的做法,但对于大文件,则不行。

    见:SDK repeatedly complaining "Not all bytes were read from the S3ObjectInputStream

    如果您经常看到这种情况,并且您正在使用 ORC 和 Parquet 等列式数据格式,请通过将属性 fs.s3a.experimental.fadvise 设置为 random,将输入流切换为随机 IO 而不是顺序。这会阻止它尝试读取整个文件,而只读取小块。对完整文件读取(包括 .gz 文件)非常不利,但会转换列 IO。

    请注意,在 S3A 中针对 Hadoop 3.x 进行了小修复,最终关闭 HADOOP-14596。是否向后移植取决于 EMR 团队。

    +我将在 S3A 故障排除文档中添加一些文本。 ASF 从未发布过有此问题的 hadoop 版本,但如果人们在玩混搭 AWS 开发工具包(非常脆弱),那么这可能会浮出水面

    【讨论】:

    • 添加 s3a 代替 s3/s3n 对我有用。谢谢。
    • 您能否更准确地说明“但转换列 IO”的含义?我真的不明白你的意思。
    • Parquet 和 ORC 不会像 CSV 文件那样将数据存储在“日期”、“用户”、“花费”行中,而是在列中存储数 MB 的日期值, 几 MB 的用户字段等。当任何 SELECT 查询只需要一小部分列时,Spark &c 只读取文件的一小部分,跳过所有您没有要求的列
    • 是的,抱歉我的问题不够精确! (我已经知道柱状格式),但在我看来,即使我没有将fs.s3a.experimental.fadvise 指定为random,spark 已经具有您提到的简洁行为;所以我的问题是“它真的会改变任何东西来激活那个标志吗?”。既然你说它会“转换列 IO”,这让我怀疑我的先入为主的想法,我想知道你是否可以对此有所了解。
    • 而不是执行一个大的 GET 0-EOF,而是执行 G 偏移量 min(read-len, fs.s3a.readahead)。如果你好奇的话,HADOOP-13203。顺序读取(CSV、gzip)的性能崩溃,这就是它不是默认值的原因。
    【解决方案2】:

    注意:这仅适用于非 EMR 安装,因为 AWS 不提供 s3a


    在根据 Steve Loughran 的回答选择忽略警告或通过设置更改输入流之前,请绝对确保您没有使用 s3://bucket/path 表示法。

    从 Spark 2 开始,您应该通过 s3a://bucket/path 使用 s3a 协议,这可能会解决您看到的警告(它对我们有用)并显着提高 S3 交互的速度。 See this answer for detail on a breakdown of differences.

    【讨论】:

    • -您对“纯” ASF 版本是正确的,但 EMR 使用 s3:// 作为前缀...当使用 s3 时,因为 EMR 团队不支持 s3a
    • 绝对准确,因此我的答案顶部有注释。不幸的是,EMR 仍然不支持s3a - 它已经存在了一段时间了。
    • 是的,你是对的。 EMR 卡在 Hadoop 2.8 上,即 EOL。认为他们已经放弃了。 “并非所有字节都被读取”有两个原因:当您在非空流上调用 close() 时,它耗尽而不是中止它(修复:当 #of bytes 和 i> 当你调用 abort() 时,即使你知道他们在做什么,他们也会告诉你。他们最终修复了 #2
    猜你喜欢
    • 2018-01-19
    • 2020-02-07
    • 2019-08-14
    • 2020-03-01
    • 2017-10-29
    • 1970-01-01
    • 2021-09-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多