17
11

More than 5 years have passed since last update.

Dir.mktmpdirで一時的なディレクトリを作成する

Last updated at Posted at 2014-02-07

Dir.mktmpdir 使ってますか?

Ruby プログラム中で temporary なディレクトリを作成したいことありますよね。
その時に役立つのが Dir.mktmpdir です。

Dir.mktmpdir の使い方

require 'tmpdir'

としてから、

Dir.mktmpdir {|dir| p dir }
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-1906-1golnp6"

もしくは、

Dir.mktmpdir do |dir|
  p dir
end
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-1906-h3po3k"

のようにして使います。

Dir.mktmpdir を実行するたびに新しい一時ディレクトリが作成されます。

Dir.mktmpdir の挙動について

Dir.mktmpdirにブロックを渡すと、ブロックを抜ける時に自動的に削除されます。

tmpdir = Dir.mktmpdir do |dir|
  p dir 
  #=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-1906-1g0qgbr"

  Dir.exists? dir 
  #=> true

  dir
end

p tmpdir 
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-1906-11g0nps"

# ブロックを抜けると自動的に削除されます
Dir.exists? tmpdir
#=> false

また、ブロックを渡さない場合、Dir.mktmpdir で作成したディレクトリは自動的に削除されないため、明示的に削除する必要があります。

tmpdir = Dir.mktmpdir
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-1906-51kzdt"

begin
  Dir.exists? tmpdir
  #=> true

  File.open("#{tmpdir}/foo", "w") { |fp|
    fp.puts "hogehoge"
  }
ensure
  # tmpdir を削除
  FileUtils.remove_entry_secure tmpdir
end

Dir.exists? tmpdir
#=> false

Dir.mktmpdir で作成されるディレクトリのプレフィクス(接頭辞)を変更する

Dir.mktmpdir の第1引数に文字列を与えると、プレフィクスを変更することができます。

Dir.mktmpdir("hoge") {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/hoge20140207-1906-1acnw8q"

Dir.mktmpdir("fuga") {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/fuga20140207-1906-1bnrbvj"

Dir.mktmpdir("piyo") {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/piyo20140207-1906-b6x8qf"

第1引数が nil または省略されると、プレフィクスは d になります。

Dir.mktmpdir(nil) {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-1906-icruez"

Dir.mktmpdir {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-1906-1075ir0"

Dir.mktmpdir で作成されるディレクトリのサフィックス(接尾辞)を変更する

Dir.mktmpdir の第1引数に文字列の配列を渡すことでプレフィクスとサフィックスを変更することができます。

Dir.mktmpdir(["hoge","fuga"]) {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/hoge20140207-1906-rwn5jbfuga"
# 第1引数の配列の3つ目移行の要素は無視される
Dir.mktmpdir(["hoge","fuga","piyo"]) {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/hoge20140207-1906-jyvsy7fuga"

# 第1引数の配列の1つ目を nil にするとプレフィクスが省略される。
# (デフォルトの`d`もつかない)
Dir.mktmpdir([nil,"fuga"]) {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/20140207-1906-5utqtmfuga"

Dir.mktmpdir で一時ディレクトリが作成されるディレクトリのパスについて

Dir.mktmpdir の一時ディレクトリはどこに作成されるのでしょうか?

デフォルトでは Dir.tmpdir で返ってくるディレクトリパス以下に作成しているようです。
OSや環境によって Dir.tmpdir の値は異なりますが、Mac OS X に於いては環境変数 $TMPDIR または /tmp になるようです。
なお、Dir.mktmpdir の第2引数でパスを指定することにより、一時ディレクトリが作成される場所を変更することができます。

## デフォルト

Dir.mktmpdir {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-12915-1r83rgl"
## Dir.mktmpdir の第2引数でパスを指定する

Dir.mktmpdir(nil, "/var/tmp") {|dir| p dir}
#=> "/var/tmp/d20140207-12915-1bkxe2m"
## Dir.tmpdir の値を確認する

Dir.tmpdir
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T"

Dir.mktmpdir {|dir| p dir}
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/d20140207-12915-zxtexn"
## 環境変数 $TMPDIR を書き換える

p ENV['TMPDIR']
#=> "/var/folders/xm/gdpmzj1x7_ng04dk88dd0sb80000gp/T/"

ENV['TMPDIR'] = "/var/tmp"
p ENV['TMPDIR']
#=> "/var/tmp"

Dir.tmpdir
#=> "/var/tmp"

Dir.mktmpdir {|dir| p dir}
#=> "/var/tmp/d20140207-12915-182s4yn"
## 環境変数 $TMPDIR に存在しないディレクトリを指定する

ENV['TMPDIR'] = "/hogehoge/fugafuga/piyopiyo"
p ENV['TMPDIR']
#=> "/hogehoge/fugafuga/piyopiyo"

Dir.exists? ENV['TMPDIR']
#=> false

Dir.tmpdir
#=> "/tmp"

Dir.mktmpdir {|dir| p dir}
#=> "/tmp/d20140207-12915-161229z"
## 環境変数 $TMPDIR を空にする

ENV['TMPDIR'] = nil
p ENV['TMPDIR']
#=> nil

Dir.tmpdir
#=> "/tmp"

Dir.mktmpdir {|dir| p dir}
#=> "/tmp/d20140207-12915-1ltqeva"

以上のことから、以下の順番でDir.mktmpdirのパスが決まるようです。

  1. Dir.mktmpdir の第2引数で指定したパス
  2. 1.が指定されていない場合は Dir.tmpdir の値
    1. 環境変数 $TMPDIR の値
    2. $TMPDIR が見つからない場合や $TMPDIR にアクセスできない場合は /tmp

参考URL

17
11
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
17
11