我必须使用Spark进行100000个顺序HTTP请求。我必须将响应存储到S3中。我说是连续的,因为每个请求返回大约50KB的数据,并且我必须保留1秒,以便不超出API速率限制。
在哪里进行HTTP调用:是从Spark Job的代码(在驱动程序/主节点上执行)还是从数据集转换(在工作程序节点上执行)?
map
或mapPartition
内发出HTTP请求,将单个数据集保存到S3。它更简单,它代表了我的求助的本质-由于1秒钟的延迟,它们是连续的。但是:
实际上,它不会从并行处理中受益,因为由于请求,您必须保持1秒的间隔。唯一的好处是可以从驱动程序中移动计算(即使它们不太难)。但是:
答案 0 :(得分:1)
将文件<32MB(或任何fs.s3a.block.size)保存到S3约为2xGET,1xLIST和PUT;对于这些调用,您都会被AWS收取一些费用,再加上存储费用。
对于较大的文件,在第一个块之后执行一次POST以启动分段上传,每32 MB一次POST(显然为32MB),最后完成JSON文件的POST。所以:效率更高
在较小的S3大小中,AWS和后续Spark查询的费用很重要:您在spark,pyspark,SQL等中使用的任何东西。许多小文件速度较慢:在S3中列出文件的成本很高,并且每个任务都被推送到火花工作者那里要花一些设置/提交/完成的费用。
关于在工作程序内部执行HTTP API调用,那么,您可以在那里做有趣的事情。如果结果不可复制,则任务失败和重试可能会给出错误的答案,但对于GET,应该可以。困难的是节制工作。我会让你在那里提出一个策略。
这里是uploading files to S3 or other object store in workers的示例;首先,建立复制src / dest操作的RDD,然后将其推出给工作人员。如果有人想尝试汇总统计信息,则工作程序代码的结果将包括上传持续时间长度信息(尽管在某些时间序列视图中您可能需要时间戳)
鉴于您必须将工作序列化为一个请求/秒,因此10万个请求将花费一天的时间。如果每个请求花费的时间少于1秒,则最好在单台计算机上运行它。重要的是逐步保存工作,以便在工作途中失败时可以从最后一个检查点重新开始。我个人将重点放在该问题上:如何进行此操作以节省每15-20分钟的工作,然后重新启动就可以从那里继续进行。
Spark不处理失败作业的恢复,仅处理任务失败。失去驱动程序,您便可以重新启动上一个查询。分手。
想到的可能是 *第一个RDD会获取查询列表以及有关任何现有检查点数据的一些摘要信息,计算接下来的15分钟的工作, *建立GET调用列表以委派给1个以上的worker。每行1个URL,或者在一行中有多个URL *运行该作业,保存结果 *测试恢复可以在较小的窗口范围内工作,并且可以消除故障。 *一次开心:全力以赴
也许还:识别并响应远端发生的任何油门事件 1.在工人中睡觉 1.返回结果中的节气门事件计数,以便驱动程序可以最初收集汇总统计信息,并可能在以后为后续任务调整睡眠窗口。