我的文件名包含我在管道中所需的信息,例如,数据点的标识符是文件名的一部分,而不是数据中的字段。例如,每个风力涡轮机都会生成一个文件turbo-loc-001-007.csv。例如,我需要管道中的loc数据。
答案 0 :(得分:3)
Java(sdk 2.9.0):
Beams TextIO读取器无法访问文件名本身,在这些用例中,我们需要使用FileIO来匹配文件并访问文件名中存储的信息。与TextIO不同,在FileIO读取的下游转换中,用户需要注意文件的读取。读取FileIO的结果是PCollection,ReadableFile类包含作为元数据的文件名,可以与文件内容一起使用。
FileIO确实具有方便的方法readFullyAsUTF8String(),它将整个文件读入String对象,这将首先将整个文件读入内存。如果需要考虑内存,则可以使用实用程序类(如FileSystems)直接处理文件。
发件人:Document Link
PCollection<KV<String, String>> filesAndContents = p
.apply(FileIO.match().filepattern("hdfs://path/to/*.gz"))
// withCompression can be omitted - by default compression is detected from the filename.
.apply(FileIO.readMatches().withCompression(GZIP))
.apply(MapElements
// uses imports from TypeDescriptors
.into(KVs(strings(), strings()))
.via((ReadableFile f) -> KV.of(
f.getMetadata().resourceId().toString(), f.readFullyAsUTF8String())));
Python(sdk 2.9.0):
对于2.9.0 for python,您将需要从Dataflow管道外部收集URI列表,并将其作为参数输入到管道中。例如,利用FileSystems通过Glob模式读取文件列表,然后将其传递给PCollection进行处理。
一旦看到文件PR https://github.com/apache/beam/pull/7791/可用,以下代码也将是python的选项。
import apache_beam as beam
from apache_beam.io import fileio
with beam.Pipeline() as p:
readable_files = (p
| fileio.MatchFiles(‘hdfs://path/to/*.txt’)
| fileio.ReadMatches()
| beam.Reshuffle())
files_and_contents = (readable_files
| beam.Map(lambda x: (x.metadata.path,
x.read_utf8()))