【问题标题】:AWS Glue Job FlowAWS Glue 作业流程
【发布时间】:2019-11-19 12:38:45
【问题描述】:

我在 Glue 中有一个 ETL 作业,它处理一个非常大(300M 行)的 JDBC 数据库表,但我真的只需要这个表的一个子集(某些 id)。当我执行glueContext.create_dynamic_frame.from_catalog(database="legislators", table_name="persons") 时,这是否会在此命令中加载整个表?有没有办法编写自定义查询以仅加载我需要的数据?或者,如果我在此之后使用另一个命令说 Filter 或 DataFrame 上的 spark SQL 命令,是否会在提取数据时进行过滤?

【问题讨论】:

    标签: python amazon-web-services apache-spark pyspark aws-glue


    【解决方案1】:

    好吧,当你运行时:

    glueContext.create_dynamic_frame.from_catalog(database="legislators", table_name="persons")
    

    它只创建一个 Spark DF 引用。

    Spark 可用于转换(即过滤、映射、选择)和操作(即收集、计数、显示)。你可以在这里How Apache Spark’s Transformations And Action works 阅读更多关于它的信息,但基本上,只有在调用action 时,你的数据库表才会加载到内存中。这是 Spark 如此强大并被推荐用于任何大小的数据集的众多原因之一。

    PDF 显示所有可用的转换和操作以及一些使用它们的示例。

    所以是的,您需要先执行一些步骤,例如:

    df = glueContext.create_dynamic_frame.from_catalog(database="legislators", table_name="persons")
    df = df.filter(YOUR_FILTER).select(SPECIFIC_COLS)
    
    # Calling an action to show the filtered DF
    df.show()
    

    这将保证您只将特定的列和行加载到内存中

    【讨论】:

    • 我想知道,它真的会编辑 SQL 语句,从而减少数据吗?或者只是拉整个表并根据转换进行过滤?由于网络限制,我们正试图限制通过网络传输的数据量。
    • 这取决于您的代码是如何编写的。我发现这个answer 很好地解释了如何避免将所有数据库加载到内存中。
    • 从那个答案看来,.filter() 确实会拉取所有行并在 Spark 端过滤它们,而不是在 DB 级别 - 所以它实际上不会在线路上节省任何空间。看起来我需要以某种方式在查询级别执行此操作。也许使用spark.sql(...)
    • 其实用filter()查询或者直接在.sql()查询可以做同样的过程。在这两种情况下,Spark 都会创建一个执行计划并在执行前对其进行优化。要查看 spark 将如何执行您的函数和查询,您应该调用 .explain() 方法
    • 我的意思是,写.sql() 不能保证 spark 会直接在数据库中执行您的查询
    猜你喜欢
    • 1970-01-01
    • 2018-08-05
    • 1970-01-01
    • 1970-01-01
    • 2019-02-21
    • 1970-01-01
    • 2019-02-18
    • 2021-10-23
    • 1970-01-01
    相关资源
    最近更新 更多