Rubyでワンライナーの時に使うオプションとかグローバル変数まとめ
rubyをワンライナーなんかで使う時に
よく使うrubyコマンドのオプションとかグローバル変数等を中心にまとめました
グローバル変数
コンフィギュレーション系
- $LOAD_PATH, $: : require時の検索対象パスの配列
IOストリーム、文字列処理系
- $_ : 最後にgetsまたはreadlineで読み込んだ文字列
- $< : コマンド行で指定されたファイルまたは標準入力へのIOオブジェクト、Kernel.gets等の読み出しはこれが使われる
- $stdin : 標準入力ストリーム
- $stdout, $> : 標準出力ストリーム、Kernel.puts、print、printf等の表示メソッドの出力先
- $stderr : 標準エラー出力ストリーム
- $FILENAME : 現在ARGFから読み出されているファイル名
- $. : 現在の入力ファイルの最後に読み込んだ行番号
- $/ : 入力レコードセパレータで、デフォルトは改行
- $\ : 出力レコードセパレータで、デフォルトはnul、-lオプション時は$/と同じになる
- $, : Array.joinのセパレータで、デフォルトはnil
- $; : splitが使うセパレータで、デフォルトはnil、-Fオプション時は値を指定できる
- $F : nまたはpオプションとaオプションを指定した時にsplitが返す値
正規表現系
- $& : 現在のスコープで最後に成功した正規表現のパターンマッチ文字列
- $~ : 現在のスコープで最後に成功した正規表現マッチオブジェクト
- $` : 現在のスコープで最後に成功した正規表現マッチ文字列よりも前の文字列
- $' : 現在のスコープで最後に成功した正規表現マッチ文字列よりも後の文字列
- $+ : 現在のスコープで最後に成功した正規表現マッチのグループに対応する文字列
例外処理系
- $? : 最後に終了したプロセスの終了ステータス
- $! : 最後に発生した例外のオブジェクト
- $@ : 最後に発生した例外のスタックとレース、$!.backtraceと同義
コマンドラインオプション
-e : [-e 'command']の形式でcommand文字列を実行する
$ ruby -e 'p "hello!"'
# -eオプション使用時はif等の条件式に単独の正規表現リテラルを
# 記述した場合、暗黙的に$_との比較となる
# 下の例はlsの結果のうち先頭がMの行を抽出
$ ls | ruby -ne 'print if /^M/' # printは引数無しの時は$_を出力する
-r : プログラムの実行前にrequire 'hogehoge'を行う
$ ruby -r 'date' -e 'p DateTime.now'
-n :
awkっぽい感じ。
標準入力を1行ずつ取得し[$_]にセット。
その後、eオプションで設定した処理を実行する
# ドットから始まるファイル、ディレクトリ名を抽出
$ ls -a | ruby -ne 'print if /^\.\w+$/'
-p : 処理の最後に$_の値を出力する
$ echo "test abc" | ruby -pe '$_.upcase!'
-a : nまたはpと組み合わせて使うと各行がsplitされて$F変数に格納されてくる
# lsの結果のうち<bash>が含まれるレコードを抽出し、splitされた配列の
# 1番目と最後の列(権限とファイル名)を表示する
$ ls -al | ruby -ane 'p "#{$F[0]} : #{$F[-1]}" if /bash/'
使用例
例えばapacheのログをちょっと確認してみるケース。
ログの中から400系か500系のステータスのレコードを抽出し、
日付部分の不要な文字列を削除してhttpステータス URL アクセス日時を表示する
bashのコマンドでやるとこんな感じ
cat access_log | awk '{print $9,$7,$4}' | grep -P '^[45]\d{2}' | sed -e "s/\[//g"
これをrubyで置き換えるとこんな感じ
ruby -nae 'p "#{$F[8]} #{$F[6]} #{$F[3].gsub("[","")}" if $F[8] =~ /^[45]\d{2}/' access_log
個人的には一つの言語でワンライナーで書いた方が微妙な仕様の違いに惑わされなくて済むし、
使い捨てコードは後者を選択する事が多いかも。