Kentaro Kuribayashi's blog

Software Engineering, Management, Books, and Daily Journal.

EmacsでPerlのモジュール名を動的に補完する

追記: id:rubikitchさんに、auto-revert-modeってのを教えていただきました!素晴しい!!!1

/path/to/pmlistをauto-revert-modeした状態にしておけばcronの更新が反映されるはず。

そこで(global-)?auto-revert-modeですよ - (rubikitch loves (Emacs Ruby CUI Books))

というわけで、そっちを使うように書き直した。

EmacsでPerlのモジュール名を補完する - subpop - subtech」で書いたネタだったりするのだけど、ともあれ、Perlモジュール名を補完(dabbrev)したいよー的な要求について。上記リンク先で書いたのは、cperl-mode初回起動時にコマンドを流していて、すごく重くていらいらしてたので、あらかじめモジュールの一覧だけのファイルを作るようにした。依然として、アホっぽいけど。

下記のようなてけとースクリプトを用意し、cronで定期的に回す。

# make_pmlist.sh
# 0 * * * * /path/to/make_pmlist.sh /path/to/pmlist

find `perl -e 'print join(q{ }, grep {-e $_} @INC);'` -name '*.pm' -type f |
xargs egrep -h -o 'package [a-zA-Z0-9:]+;' |
perl -nle 's/package\s+(.+);/$1/; print' |
sort |
uniq > $1

んでもって、Emacsの設定ファイルにこんな感じで追記。

(defvar perl-pmlist-file-name "/path/to/pmlist")
(defvar perl-pmlist-buffer-name "*PerlModules*")
(defvar perl-pmlist-make-command (concat "/path/to/make_pmlist.sh"
                                         " "
                                         perl-pmlist-file-name))

(defun perl-make-pmlist-buffer ()
  (interactive)
  (save-excursion
    (when (interactive-p)
      (shell-command perl-pmlist-make-command))
    (unless (get-buffer perl-pmlist-buffer-name)
      (find-file perl-pmlist-file-name)
      (rename-buffer perl-pmlist-buffer-name)
      (auto-revert-mode t))))

(add-hook 'cperl-mode-hook 'perl-make-pmlist-buffer)

これで、cperl-mode初回起動時に、あらかじめ作っておいたPerlモジュール一覧を読み込んだバッファを作成しておくので、dabbrevの候補に上がってくる感じ。んでもって、一覧がcronで更新されたら、auto-revert-modeによりEmacsのバッファ上も自動的に反映される。モジュールの新規インストール後に、cronによる更新をを待たずに手動で反映させるには、M-x perl-make-pmlist-bufferを実行すればよい(これはちょっと時間がかかる)。

一覧をあらかじめ作っておくってのがすごくアレな感じだが、まぁないよりはマシかなぁとは思われる。もっとかっけー方法があったら教えてください><