【问题标题】:Sparklyr: List contents of directory in R using invoke methodsSparklyr:使用调用方法列出 R 中目录的内容
【发布时间】:2019-03-26 16:03:30
【问题描述】:

无法找到用于通过 Spark 列出目录内容的内置 sparklyr,我正在尝试使用 invoke

sc <- spark_connect(master = "yarn", config=config)
path <- 'gs:// ***path to bucket on google cloud*** '
spath <- sparklyr::invoke_new(sc, 'org.apache.hadoop.fs.Path', path) 
fs <- sparklyr::invoke(spath, 'getFileSystem')
list <- sparklyr:: invoke(fs, 'listLocatedStatus') 
Error: java.lang.Exception: No matched method found for class org.apache.hadoop.fs.Path.getFileSystem
    at sparklyr.Invoke.invoke(invoke.scala:134)
    at sparklyr.StreamHandler.handleMethodCall(stream.scala:123)
    at sparklyr.StreamHandler.read(stream.scala:66) ...

注意:是否有关于分布式代码可重现示例的指南?鉴于我正在针对特定的 Spark 环境运行,我不知道如何制作其他人可以效仿的示例。

【问题讨论】:

标签: r apache-spark sparklyr


【解决方案1】:

getFileSystem方法takesorg.apache.hadoop.conf.Configuration对象作为第一个参数:

public FileSystem getFileSystem(Configuration conf)
                     throws IOException

返回拥有此路径的文件系统。

参数

conf - 解析文件系统时使用的配置

因此,检索FileSystem 实例的代码应该或多或少像这样:

# Retrieve Spark's Hadoop configuration
hconf <- sc %>% spark_context() %>% invoke("hadoopConfiguration")
fs <- sparklyr::invoke(spath, 'getFileSystem', hconf)

另外listLocatedStatustakes either Path

public org.apache.hadoop.fs.RemoteIterator<LocatedFileStatus> listLocatedStatus(Path f)
                                                                     throws FileNotFoundException,
                                                                            IOException

Path and PathFilter(注意这个实现是protected):

public org.apache.hadoop.fs.RemoteIterator<LocatedFileStatus> listLocatedStatus(Path f)
                                                                    throws FileNotFoundException,
                                                                            IOException

因此,如果您想按上述方式构建代码,则必须至少提供一条路径

sparklyr:: invoke(fs, "listLocatedStatus", spath)

在实践中,直接获取FileSystem 可能更容易:

fs <- invoke_static(sc, "org.apache.hadoop.fs.FileSystem", "get",  hconf)

并使用globStatus

lls <- invoke(fs, "globStatus", spath)

其中spath 是带有通配符的路径,例如:

sparklyr::invoke_new(sc, 'org.apache.hadoop.fs.Path', "/some/path/*")

结果将是一个 R list,可以轻松迭代:

lls  %>%
    purrr::map(function(x) invoke(x, "getPath") %>% invoke("toString"))

学分

The answerHow can one list all csv files in an HDFS location within the Spark Scala shell?@jaime

注意事项

  • 一般来说,如果您与重要的 Java API 进行交互,那么使用 Java 或 Scala 编写代码并提供最小的 R 接口会更有意义。
  • 对于与特定文件对象存储的交互,使用专用包可能更容易。对于 Google Cloud Storage,您可以查看 googleCloudStorageR

【讨论】:

  • 如何从 flist 中获取内容? > flist flist org.apache.hadoop.fs.FileSystem$4 org.apache.hadoop.fs.FileSystem$4@71ab657
  • 这是一个很好的建议,但是,我目前不知道/在 Java 或 Scala 中工作。有没有更好的推荐方式让 sparklyr 用户列出目录的内容?我没有发现 sparklyr 内置此功能。
  • 据我所知,没有内置的帮助程序。关于您的第一点 - 如果您不了解 Scala 或 Java,那么直接使用 invoke 将是一场噩梦。直接使用 JVM 语言是一个更好的选择 - 体面的 IDE 可以帮助您处理大部分样板文件并帮助您确定和排除错误。
  • 所有这些都有效,直到我得到 listLocatedStatus 的结果。它是 R 中的环境,而不是可迭代的。它具有类属性 'spark_jobj' 'shell_jobj'
  • 只有基本对象(数组、基元、盒装基元)被转换为等效的 R 对象。其余部分按原样提供 - 作为 java 对象的句柄。此外,看起来sparklyr 在幕后做了一些意想不到的事情,试图访问非公共成员,但我不明白为什么会这样。
猜你喜欢
  • 2019-09-05
  • 1970-01-01
  • 2011-01-19
  • 2011-07-14
  • 2010-11-03
  • 1970-01-01
  • 1970-01-01
  • 2017-02-17
  • 2015-03-10
相关资源
最近更新 更多