LoginSignup
17
17

More than 5 years have passed since last update.

RubyでLinuxコマンドの再実装(tree編)

Last updated at Posted at 2014-10-16

Rubyの勉強にRubyで有名ドコロのLinuxコマンドたちを再実装してみたいとおもいます。

少しずつ追記する形にできればと思っています。よりよい実装方法などありましたらぜひご教授いただけると幸いです。

RubyでLinuxコマンドの再実装(ls編) - Qiita
RubyでLinuxコマンドの再実装(tree編) - Qiita

tree

treeコマンドに挑戦します。
treeコマンドは, 指定したディレクトリ以下のファイルを木構造にして表示してくれます。

スクリーンショット 2014-10-16 16.16.08.png

tree.rb
#! /usr/bin/env ruby -w
#
# tree: 引数で指定されたディレクトリ以下のファイルを
#       再帰的に木構造として表示する.

require 'optparse'

options = ARGV.getopts('aF')

# parentは絶対パス.
def display_entries(parent, prefix, options)
  # '.', '..'を除く. 無限に再帰することを防ぐ
  entries = Dir.entries(parent).delete_if do |entry|
    entry == '.' or entry == '..' or !options['a'] && entry.start_with?('.')
  end

  entries.each_with_index do |entry, index|
    fullpath = File.join(parent, entry)
    entry = f_option(parent, entry) if options['F']
    # 最後の要素かどうか
    if index == entries.size - 1
      puts "#{prefix}└── #{entry}"
      next_prefix = prefix + '    '
    else
      puts "#{prefix}├── #{entry}"
      next_prefix = prefix + '│   '
    end
    if File.directory? fullpath
      display_entries(fullpath, next_prefix, options)
    end
  end
end

def f_option(parent, entry)
  case File.ftype(File.join(parent, entry))
  when "file"
    if File.executable? File.join(parent, entry)
      "#{entry}*"
    else
      entry
    end
  when "directory"
    "#{entry}/"
  when "link"
    "#{entry}@"
  else
    entry
  end
end

target = ARGV[0] || '.'
target_fullpath = File.absolute_path target
init_prefix = ''

puts target
display_entries target_fullpath, init_prefix, options

ファイルのタイプを調べる際の処理をls編とちょっとだけ変えてみました。
シンボリックリンクのリンク先を表示する修正が必要ですね...
colorlsのときとほとんど変わらないので省きました。
File.ftypeでは実行可能ファイルかどうかは判定できないんですかね??そこがちょっと気になります。
あとはオプションのあたりなど複雑になってしまっているので綺麗にしたいです。

17
17
1

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
17