Amazon web services 为什么pyspark中S3目录源的输入文件为空?
我试图获取通过AWS Glue中的S3数据目录加载的每个文件的输入文件名(或路径) 我在一些地方看到,Amazon web services 为什么pyspark中S3目录源的输入文件为空?,amazon-web-services,apache-spark,amazon-s3,pyspark,aws-glue,Amazon Web Services,Apache Spark,Amazon S3,Pyspark,Aws Glue,我试图获取通过AWS Glue中的S3数据目录加载的每个文件的输入文件名(或路径) 我在一些地方看到,input\u file\u name() 因此,下面的代码似乎应该可以工作,但总是为每个输入文件名返回空值 导入系统 从awsglue.context导入GlueContext 从awsglue.job导入作业 从awsglue.utils导入getResolvedOptions 从pyspark.context导入SparkContext 从pyspark.sql.functions导入输入
input\u file\u name()
因此,下面的代码似乎应该可以工作,但总是为每个输入文件名返回空值
导入系统
从awsglue.context导入GlueContext
从awsglue.job导入作业
从awsglue.utils导入getResolvedOptions
从pyspark.context导入SparkContext
从pyspark.sql.functions导入输入文件名
args=getResolvedOptions(sys.argv,['JOB_NAME','TempDir']
sc=SparkContext()
gc=GlueContext(sc)
spark=gc.spark\u会话
作业=作业(gc)
job.init(args['job\u NAME',args)
#从Glue目录中获取源帧,该目录描述S3中的文件
fm_source=gc.create_dynamic_frame.from_catalog(
database='database\u name',
table_name='table_name',
转换\u ctx='fm_source',
)
df_source=fm_source.toDF()。带列('input_file_name',input_file_name())
df_源显示(5)
结果输出:
+-------------+---------------+
|other_columns|input_file_name|
+-------------+---------------+
| 13| |
| 33| |
| 53| |
| 73| |
| 93| |
+-------------+---------------+
是否有其他方法可以确保填充input\u file\u name()
来创建框架?我现在尝试通过create\u dynamic\u frame.from\u catalog
,create\u dynamic\u frame.from\u options
和getSource().getFrame()
,创建一个源代码框架,但我得到的结果是每个框架都有一个空的输入文件名
列。我相信在使用该选项时这是不可能的,鉴于幕后胶水是连接文件以创建最佳数量的输入。因此,鉴于原始文件路径不再是直接输入,input\u file\u name
的概念在此上下文中没有意义
然而,这些文档在某种意义上有点误导性,即即使对于少于50000个文件的输入,如果不明确禁用该选项,也会根据文件大小触发Glue来连接输入。在我们的例子中,我们有数千个微小的输入文件(我还添加了我的经验,在我的例子中,由于调用cache()
方法,我收到了一个空结果
例如:
import pyspark.sql.functions as F
df = spark.read.json("/my/folder/test.json")
df.cache()
df = df.withColumn("input_file_name", F.input_file_name())
df.show()
我收到
+-------------+---------------+
|other_columns|input_file_name|
+-------------+---------------+
| 13| |
| 33| |
| 53| |
| 73| |
| 93| |
+-------------+---------------+
但是如果我删除行df.cache()
则列input\u file\u name
将正确显示输入文件名
解决方法可能是调用F.input\u file\u name()
在缓存之前。我面临与Vzzarr相同的问题。当我在数据帧上调用缓存后创建输入文件路径
列时,文件路径是空的。但是当我在调用缓存
之前创建输入文件路径
时,它工作了。我发现另一个奇怪的行为。当我添加 limit()
beforeinput\u file\u路径
id也不起作用
此代码的文件名为空
df_raw = (spark
.read
.option("delimiter", ";")
.csv(filepath,header = "true",inferSchema=True)
.select("COL1","COL2")
.limit(1000)
)
df_transform = (df_raw
.withColumn("filename", f.input_file_name())
)
此代码有效
df_raw = (spark
.read
.option("delimiter", ";")
.csv(filepath,header = "true",inferSchema=True)
.select("COL1","COL2")
)
df_transform = (df_raw
.withColumn("filename", f.input_file_name())
.limit(1000)
)
Toook给了我一些时间来解决这个问题,因为我试图通过只读取几行来加快调试速度。这可能是由于启用了groupFiles
选项(请参阅).但是,我不确定是否可以禁用它以从catalog@YuriyBondaruk谢谢!如果我正确阅读了文档,它似乎应该自动禁用少于50000个文件(我的测试桶有~100个)。即使不从目录中读取,我也看不到禁用该选项的语法。这是否也意味着如果我的目录包含(自动)分区,则会调用单文件操作,如input\u file\u name()
永远不会起作用?对于其他正在查看的人,当您希望对大于50000个文件的输入显式禁用此功能时,相关的groupFiles
设置为none
。我不确定如果直接从目录读取,是否可以禁用此选项。我使用直接从s3加载数据时使用了此选项E> > Read TyrimixFrimeFraseOrthOpType(…)<代码>函数,您是否尝试将数据读入数据帧,然后将其转换为动态框架?卓越的洞察力!此ALO对我起作用。如果需要在交互式火花会话(即Jupyter笔记本)中删除缓存表,请考虑使用<代码> ScPc.CordC.CurrCaseCe()/<代码>是的!!这就是问题所在,但为什么?我应该稍后缓存吗?