【问题标题】:How to get hadoop put to create directories if they don't exist如果它们不存在,如何让hadoop创建目录
【发布时间】:2014-06-24 18:28:38
【问题描述】:

我一直在使用 Cloudera 的 hadoop (0.20.2)。 在这个版本中,如果我把一个文件放入文件系统,但目录结构不存在,它会自动创建父目录:

例如,如果我在 hdfs 中没有目录并输入:

hadoop fs -put myfile.txt /some/non/existing/path/myfile.txt

它将创建所有目录:some、non、existingpath 并将文件放入其中。

现在,有了更新的 hadoop (2.2.0) 产品,这种目录的自动创建不会发生。 上面的相同命令产生:

put: `/some/non/existing/path/': 没有这样的文件或目录

我有一个解决方法,可以先对每个 put 执行 hadoop fs -mkdir,但这不会很好。

这是可配置的吗? 有什么建议吗?

【问题讨论】:

  • 为什么表现不好?
  • >> 为什么性能不好?因为对于每个“放置”,我都在做一个 mkdir - 大多数时候可能不需要它,所以它会影响高吞吐量情况下的性能。
  • 您是否考虑过编写自己的解决方案?我很惊讶put 表现出色,考虑到每次调用都必须启动 VM、读取配置等...
  • 嗨,我们没有,但我想这是需要考虑的事情。我希望有一个开箱即用的简单解决方案(不创建父目录)。

标签: hadoop hdfs cloudera put biginsights


【解决方案1】:

现在你应该使用 hadoop fs -mkdir -p <path>

【讨论】:

  • 如何回答这个问题?
  • 不幸的是,它不是特别有效,因为 JVM 需要为 mkdir 命令启动,但是 '-p' 选项确实有一个很好的好处,即如果目录存在它就不会出错。使错误处理更加简洁。
【解决方案2】:

编者注:警告此答案不正确


hadoop fs ... 已弃用,而是使用:hdfs dfs -mkdir ....

【讨论】:

  • hadoop dfs -mkdir /mnt/hdfs 已弃用:不推荐使用此脚本执行 hdfs 命令。而是使用 hdfs 命令。
【解决方案3】:

将文件放入 hdfs 中不存在的目录需要两个步骤。正如@rt-vybor 所说,使用 mkdir 的“-p”选项来创建多个缺少的路径元素。但是由于OP询问了如何将文件放入hdfs,下面也进行了hdfs put,注意也可以(可选)检查put是否成功,有条件地移除本地副本。

先在hdfs中创建相关目录路径,然后将文件放入hdfs。您想在放入 hdfs 之前检查文件是否存在。您可能想要记录/显示文件已成功放入 hdfs。以下结合了所有步骤。

fn=myfile.txt
if [ -f $fn ] ; then
  bfn=`basename $fn` #trim path from filename
  hdfs dfs -mkdir -p /here/is/some/non/existant/path/in/hdfs/
  hdfs dfs -put $fn /here/is/some/non/existant/path/in/hdfs/$bfn
  hdfs dfs -ls /here/is/some/non/existant/path/in/hdfs/$bfn
  success=$? #check whether file landed in hdfs
  if [ $success ] ; then
    echo "remove local copy of file $fn"
    #rm -f $fn #uncomment if you want to remove file
  fi
fi

你可以把它变成一个shell脚本,获取一个hadoop路径和一个文件列表(也只创建一次路径),

#!/bin/bash
hdfsp=${1}
shift;
hdfs dfs -mkdir -p /here/is/some/non/existant/path/in/hdfs/
for fn in $*; do
  if [ -f $fn ] ; then
    bfn=`basename $fn` #trim path from filename
    hdfs dfs -put $fn /here/is/some/non/existant/path/in/hdfs/$bfn
    hdfs dfs -ls /here/is/some/non/existant/path/in/hdfs/$bfn >/dev/null
    success=$? #check whether file landed in hdfs
    if [ $success ] ; then
      echo "remove local copy of file $fn"
      #rm -f $fn #uncomment if you want to remove file
    fi
  fi
done

【讨论】:

    【解决方案4】:
    hdfs dfs -mkdir -p <path>
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-06-26
      • 1970-01-01
      • 2016-09-18
      • 2011-02-26
      • 2014-02-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多