kmh*_*kmh 5 json gzip hadoop scala apache-spark
从 Spark RDD 开始,我想将 JSON 数据暂存并存档到 AWS S3。只有压缩它才有意义,而且我有一个使用 hadoop 的进程GzipCodec,但是有些事情让我对此感到紧张。
当我查看org.apache.spark.rdd.RDD.saveAsTextFile这里的类型签名时:
https://spark.apache.org/docs/2.3.0/api/scala/index.html#org.apache.spark.rdd.RDD
类型签名是:
def saveAsTextFile(path: String, codec: Class[_ <: CompressionCodec]): Unit
Run Code Online (Sandbox Code Playgroud)
但是当我在这里检查可用的压缩编解码器时:
https://spark.apache.org/docs/2.3.0/api/scala/index.html#org.apache.spark.io.CompressionCodec
父特征CompressionCodec和子类型都说:
编解码器的有线协议不能保证跨版本的 Spark 兼容。这旨在用作单个 Spark 应用程序中的内部压缩实用程序
这不好……但没关系,因为无论如何,gzip 可能更容易跨生态系统处理。
类型签名说,编解码器必须是一个亚型CompressionCodec......但我尝试了以下另存为。广州,并能正常工作,即使Hadoop的GzipCodec不是<: CompressionCodec。
import org.apache.hadoop.io.compress.GzipCodec
rdd.saveAsTextFile(bucketName, classOf[GzipCodec])
Run Code Online (Sandbox Code Playgroud)
我的问题:
那么,对于初学者来说,您是否绑定到 RDD 或者可以使用 DataSets/DataFrames ?
使用 DataFrames,你可以使用类似的东西
df.write.format("json").
option("compression", "org.apache.hadoop.io.compress.GzipCodec").
save("...")
Run Code Online (Sandbox Code Playgroud)
然而,有一些考虑因素。压缩很棒,但如果您生成的文件非常大,您必须记住 gzip 不是一种可拆分格式,也就是说,如果您想稍后处理该文件,则必须由一个人读取它工人。例如,如果您的文件是不可分割的且大小为 1G,则需要 T 时间来处理,如果它是可分割的(如 LZO、Snappy 或 BZip2),则可以按 T/N 进行处理,其中 N 是分割数(假设 128MB 块,则约为 8)。这就是 Hadoop 使用 SequenceFiles(可拆分,并在一个块内使用 gzip)的原因,也是存储到 S3 时选择的压缩格式通常是 Parquet 的原因。Parquet 文件比 Gzipped 文件小,并且是可分割的,也就是说,它的内容可以由多个工作人员处理。您仍然可以使用 gzip 压缩的文本文件,但将它们保持在 ~100/200Mbyte 范围内。
归根结底,这实际上取决于您计划如何处理 S3 中的数据。
会被质疑吗?在这种情况下,Parquet 作为格式是更好的选择。
它会被读取/复制到其他不理解 parquet 的系统吗?然后gzip压缩就可以了。而且它很稳定,您不必担心它会发生变化。您可以自己尝试一下,在 S3 上保存一些示例数据,您仍然可以使用任何 gzip 工具打开它。