Guardをつかってみた
はじめに
Guardというファイル変更を検出して動作するRuby製のツールがあります. Guardは編集して保存するだけで勝手に何かバックでコマンドを走らせることができるツールです.
これをtexのコンパイルなどに使うと非常に便利でしたのでメモしておきます.
Guardのインストール
gem install guard gem install gurad-shell
guard-shellをつかうことでシェル上からGuardを常駐させたり,Guardの設定ファイルを簡単に生成できるようになります.
Guardの簡単な使い方
ここではtest.texというファイルを書くことを想定した例で説明していきます.
普通の文章でも構いませんが,ここでは例なので次のような文を書いておきます
test.tex
\documentclass[a4j]{jarticle} \begin{document} テスト \end{document}
これでGuardを導入するまでの下準備ができました.
では本題に移りましょう.
Guardの初期化をまずはしましょう
guard init
こうすることで Guardfileと呼ばれるものが生成されるはずです. 中身はrubyで記述することができます. コメントアウトがたくさん書かれてますが,必要部分はここだけです. Guardfile
guard :shell do watch(/(.*).txt/) {|m| `tail #{m[0]}` } end
Rubyを知らない方にとっては意味不明かもしれませんが,ざっくり説明すると, 現在のディレクトリ以下に存在するどれかのtxtファイルが変更されたらtailコマンドをつかって変更されたファイルの末尾を出力するというものです.
なお,m[0]にはファイル名が出力されます.
ごちゃごちゃ書いても仕方ないので例をおみせしましょう. まずはGuardfileのtxtの部分をtexに変更してください
guard :shell do watch(/(.*).tex/) {|m| `tail #{m[0]}` } end
これでtexファイルが変更されたら,そのtexファイルをtailで実行するというものになりました.
ではさっそくつぎのようにしてGuardを走らせましょう.
Guardの起動は簡単です.shell上で次のようにタイプしましょう.
guard
こうするとバックで動くので別なウィンドウで先程つくったtest.texを上書きしてみてください.何も編集しないで,保存だけすると次のような形でtexファイルをtailした結果がでるはずです.
\documentclass[a4j]{jarticle} \begin{document} テスト \end{document} [1] guard(main)>
基本的な使い方はこれだけです. これでtexを保存するたびにコンパイルする方法は察しはついたかと思います. ようするに「tail m[0]」の箇所をコンパイルするときのコマンドに書き換えてあげればいいのです.
Guardをつかってコンパイルしてみる
ここではplatexをつかってtexをコンパイルしてdviファイルを生成,dvipdfmxをつかってpdfを出力させてみます.
guard :shell do watch(/(.*).tex/) {|m| `platex test.tex && dvipdfmx test.dvi` } end
これだけです.
あとは先程のようにGuardを実行しておけば保存するたびにコンパイルされるはずです.
ただ,僕自身癖なのか,つい上書き保存を何度もしてしまうらしくて,何もファイルが変更されてないときに保存してしまって,そのたびにコンパイルがバックで動くという面倒なことをよくやってしまいます.人によってはある条件のときだけコンパイルさせたいとかそういったこともあるとは思います.
次はそのようなときにどうするかについてメモしておきます.
特定の条件のときだけアクションを起こしたい
ここでは,ファイルに何ら変更がないときにはコンパイルをしないというような設定にしてみます.
やりかたは様々あるとは思いますが,簡単に思いついた方法があったのでそれに沿って設定してみました.
では実際にやってみましょう
まずはtest.texをコピーしてbuf.texというファイルをつくります
cp test.tex buf.tex
つぎに差分をとって変化を検出するような設定をしましょう.先程つくったGuardfileを次のように編集すればokです.
Guardfile
guard :shell do watch(/(.*).tex/) {|m| s = `diff readme.tex buf.tex` if s.length > 0 then `cp readme.tex buf.tex` `platex readme.tex && dvipdfmx readme.dvi` end } end
簡単に紹介しますと,
s = `diff readme.tex buf.tex`
でreadme.texとbuf.texの差分を出力してます.その結果がsという変数に代入されます.
次のif文ではs変数に代入された文字列1文字以上あればbuf.texを更新したあとtexのコンパイルをするというものです.
このようにGuardfileはRubyが走るので様々な条件などで試せますね.
まとめ
Guardをtexをつかうときに便利な例をメモした.
ただファイルの変更を検出して動作させるためのものではなく,Rubyを使った自由な表現が可能なので使い方の幅が広がります.