IntelliJでPerlの変数宣言が複数続いた際に=の位置を揃える設定

普段Perlを書くときにIntelliJPerl pluginを使って書いているのだが、便利なことにIntelliJReformat Code時にPerl::Tidyを使ってReformatしてくれるらしい。

しかしReformatしてみたところ、変数宣言複数続いたときに = イコールの位置を揃えてくれないので、どうしたものかと困っていた。

例えば以下のような変数宣言のときに

my $short = 'short variable';
my $long_long_long = 'long variable';

= イコールの位置が揃うようにReformatしてほしい。

my $short     = 'short variable';
my $long_long = 'long variable';

あれこれ見てみたらプラグインPerl::Tidyの設定が悪いわけではなく、IntelliJ側のCode Styleの設定のせいではないかと疑ってみた。試しに設定を探してみたところどんぴしゃで、思い通りにReformatされるようになった。 設定方法は以下の通り。

  • Preferences -> Editor -> Code Style -> Perl5 にいく
  • Wrapping, Braces & Alignments のタブを選択
  • Assingment expressionAlignmentDon't align から On consecutive line に変更

これで上記のフォーマットが実現出来た。 設定方法に関してはIntelliJのバージョンによって設定までのとどりつき方が変わることもありそう。

IntelliJを使ってPerlアプリケーションの開発をする

これは、はてなエンジニア Advent Calendar 2018 23日目の記事です。

昨日は id:tkzwtks さんで AWS Step Functionsを利用してAWS BatchやFargateのタスクを起動する でした。

こんにちは。普段はマンガチームでGigaViewerの開発をしています、id:miki_bene といいます。マンガチームやGigaViewerについてはこちらの記事などをどうぞ。 仕事ではPerlを使ってアプリケーション開発をしており、Perlを書くのにVimEmacsのようなテキストエディタ拡張機能を入れて書くのではなくIntelliJを使って開発をしています。始めはEmacsを使って開発をしていましたが、IntelliJを使うようになって感じ始めた便利さやIDEを使うメリットをご紹介します。

何故IntelliJ?

まず、IntelliJを使うようになったきっかけを説明します。Perlを書き始めて最初の内はEmacsに拡張を入れて書いていましたが、

  • バッファ内の文字列や拡張で定義されているトークンの補完でしか対応していないため、十分な補完を行うことが難しい
  • gtagsなどを使ったタグジャンプで定義ジャンプを行うため、時々不正確なジャンプをしてしまう

といった悩みを感じていました。Perlを本格的に書き始める前はScalaIntelliJを使って書いていたので、プログラミング言語の差だけでなく補完やコードジャンプ・リファクタリングなどといったコードを書く際の体験の差が明確にあったのも理由です。 そんな中ふと、「最近はPHPRubyPythonのような動的型付けの言語でもIntelliJベースのIDEがあるのだから、Perlにもあるのではないか」と思ったのがきっかけです。そうして見つけたのがIntelliJPerlプラグインです。

メリット

ここからはIntelliJを使ってPerlを書くことのメリットについて紹介します。

まず上げたいこととして、当たり前なことなのですがIntelliJの機能に乗っかることが出来ることですは最大のメリットだと思います。ざっと上げるだけでも

などがあります。IntelliJの静的解析の機能を使って実現されているので、正確な補完や定義ジャンプ、リファクタリングが行えます。これはかなりの体験の改善で、悩みに上げていた正確さを改善するだけでなく、GUIベースで操作出来ることの簡単さや高機能なリファクタリングツールを手に入れることが出来ました。

またPerlプラグイン独自の機能としてアノテーションがあります。プラグインPerlの構文に沿うコードは解析でき補完も効きますが、メソッド定義時にSmart::Argsなどを用いてPerlの一般的なメソッド定義に沿わなくなった場合は補完が効きません。例えば以下の2つのメソッド定義の場合、 Smart::Args を用いたfind_by_id_with_smart_args は補完されません。

package My::Package;
use Smart::Args qw(args);

# 解析可能で My::Package->find_by_id() の呼び出しが補完可能
sub find_by_id_with_normal {
    my ($class, $id) = @_;
    ...
}

# 解析不可能で My::Package->find_by_id() の呼び出しが補完できない
sub find_by_id_with_smart_args {
    args my $class => 'ClassName',
         my $id    => 'Int',
         ;
    ...
}

その様な場合は #@method というコメントをメソッド定義の直前に書いて、アノテーションとしてプラグイン側に伝えます。そうすることで、Smart::Args を使った場合でも補完されるようになります。

# アノテーションコメントを付けることで、補完できるようになる
#@method
sub find_by_id_with_smart_args {
    args my $class => 'ClassName',
         my $id    => 'Int',
         ;
    ...
}

Perlの解析の難しさをアノテーションを使って補っている形のため若干の面倒さはありますが、アノテーションに続けてメソッド自体のコメントを書くということを半強制できているため、副次的なメリットもあるなと感じています。

まだ不便な所

IntelliJを使ったメリットを紹介していきましたが、まだまだ解消できていないものもあります。

補完やコードジャンプといった機能は静的解析によって受けている恩恵のため、通常の構文とは異なるSmart::ArgsModule::Functionsといった動的に解決するようなモジュールの利用した場合は、補完や定義ジャンプなどが行えません。当然文字列結合をしたクラス読み込みやメソッド呼び出しなどのメタプログラミングを行っている部分も同様です。 またチーム内で自分しかIntelliJを使っていないことで起こることもあります。全てのメソッドにアノテーションが付いているわけでは無いため、多くのメソッドは補完がされないといったことや、逆にチームメンバーからは僕だけ不思議なコメントを付けているように見えて、レビューで指摘されたりといったこともあります。

こういった課題は新たに Smart::ArgsModule::Functions の対応プラグインを開発したり、他のエディタでもアノテーションを意味のあるようにする拡張を作ったりということで解決できますが、かなりの労力がかかり道程はまだまだ遠そうです。

終わりに

ここまでで、IntelliJを使ってPerlアプリケーションの開発をすることについてご紹介しました。チームでは今のところマイノリティのため100%快適というわけにはいきませんが、Emacsの拡張をあれこれ試していた時期と比べるとかなり改善しました。ここではコーディング時のことを中心に書きましたが、IntelliJIDEA 2018.3からGitHubのPullRequestをIntelliJから見れる機能が加わりました。

IntelliJ IDEA 2018.3 EAP: GitHub pull requests and more – IntelliJ IDEA Blog | JetBrains

最近レビューの際はこの機能を使うようにしていて、IntelliJのDiffの見やすさとエディタとの統合に驚いているところです。これは始めは考えていなかったメリットでした。これまでIntelliJのコードを書くといった部分しか使ってきませんでしたが、様々なツールの統合といったIDEの本領を発揮させていきたいと思います。

明日は id:alpicola さんです。

お部屋のCO2濃度監視始めました

以前から自室で作業していると急に眠くなったり考えるのが面倒になってしまい, 昼寝をしてしまうことが多くあった. こういう性分なので仕方がない, 部屋で作業するときは休み休みやるしかないとずっと思っていたところ, どうやら室内のCO2濃度と集中は関係しているらしいということを知った.

チームラボオフィスの空気環境(CO2)を測定して改善している話:tks(高須 正和)のブロマガ - ブロマガ

オフィスでは NETATMO を使ってCO2計測をしており, 確かに値が高くなるとぼーっとし始めるなと思ったので自室でも計測してみることにした.

計測してみる

やったのは以下の記事と全く同じことで, CO2-miniの計測器から値取り, Raspberry Pi経由で Mackerel に投げるという流れ.

CO2モニタリングのためにセンサーをHackした話 - kurainの壺 Raspberry Pi + CO2 mini で CO2 濃度を計測する – どうのこうの

ソースコードは以下. kurainさんのライブラリはパッと動かなかったので, Pythonのモジュールの方を利用した. ソースコードはサンプルコードほぼそのままで以下. gist.github.com

監視は Mackerel を使ったので, 簡単に Slack にアラートを投げれて便利.

Image from Gyazo

こちらは Slack にアラートが来て窓を開ける様子.

Image from Gyazo

おわりに

計測してみたら自室は窓や扉を閉じた状態だとグングンとほぼ線形に濃度が上昇していっている状況だというのがわかった. 最大値は観測できてないけど1800ppm以上は観測してるから2000前後にはなりそうで, どの道快適とは言えなさそう.

何年も前から部屋ではすぐ眠くなって集中できないものと思い込んでいたけれど, 実は閉め切った部屋のCO2濃度が高いせいかもしれないとわかった. 今のところ集中できているかは客観的には見れてないけれど, 少なくとも眠くなる状態は窓を開けることで改善できそうに思う.

完全に思い込みで思考停止していたのを, 計測してみて初めて現状を理解することができた. 近所の家の声が聞こえる, 逆に漏れる. タバコの煙が時々入ってくるなんかの問題があって常時開けることは難しいけれど, 開けるべきタイミングを計れるようになったのは大きい改善だった. エンジニアの格言「推測するな, 計測しろ」を実践できて良い休日を過せた.

24歳になりましたなのと, 株式会社はてなに入社していました

24歳になりました.

Twitterのページを見ると風船が飛んでいると思います.

twitter.com

今年は年齢がただインクリメントされただけでなく, 新社会人にもなりました. 4月から株式会社はてなに新卒で入社し, Webアプリケーションエンジニアをしています.

考えてみると自分の言語のスタックはScalaインターンの時期や配属されたチームでも使っているPerl・研究で割と書いていたPythonと, 偶然にもはてなの言語選定とマッチしている部分が多くて, 「これは活躍チャンスじゃん」などと思ったりしています.

とはいえやったことのあるサーバーサイド技術に固執するわけではなく, これまで取り組んでこれてなかったフロントエンドやモバイルアプリといった分野にもかかわっていきたいと思います.

今後とも各位よろしくお願いいたします.

PS

これはとあるリストです.

何でも送ることができてしまいます. http://amzn.asia/5IYrS0P

Emacsのモードラインの時刻表示を秒単位するにはdisplay-time-intervalでやる

タイトルのままのことがやりたいだけ.

以下の設定でできます.

(setq display-time-interval 1) ;; こいつで設定する. デフォルト値は60秒で, 今だと1秒毎に更新
(setq display-time-string-forms
  '((format "%s:%s:%s" 24-hours minutes seconds)))
(setq display-time-day-and-date t)
(display-time-mode t)

これでEmacsでモードラインに時刻を表示させる display-time-mode をちょっと快適にできました.

僕は時刻表示をするときはいつも秒まで表示するタイプなんだけど, Emacsで秒単位を表示させると時刻の更新間隔が1分毎なので困まった. これだと秒を表示する意味がない.

普通にググると単純に時刻を表示するための display-time-day-and-datedisplay-time-mode の記述しか出てこない. やり方わかってから見つけたけどEmacsWikititle-tile.el の部分にちょろっと書いてあったりする.

EmacsWiki: title-time.el

結局ググっても全然出てこないので, describe-variabledisplay-time-mode を調べて time.el の存在を知った. そこからそれっぽい display-time-update, display-time-event-handler を見つけ, display-time-interval を発見したという流れ.

Emacs設定情報結構ググってしまいがちだけどわからければ describe-variable で調べて定義周辺のコードを読んでしまえばわかるというのは良い体験だった.

これからもEmacs少しづつ便利にしていきたい.

追記:

emacs display-time-interval で調べたら日本語の記事がかろうじて出てきた(というか英語記事も全然出ないのだが……). このサイトがめちゃくちゃ良くてスラドなんですよ. スラド最高.

srad.jp

Emacs実践入門 出版記念イベントに参加してきた

Emacs実践入門 出版記念イベント に参加してきた.

5年前に出たEmacs実践入門の改訂版が出たことによる出版記念イベントで, 内容としては著者の 大竹智也 さんの基調講演や, 自分のエディタさばきを披露する『エディタの鉄人』, 様々な発表者の方の発表などがあった. 暗黒美無王でおなじみの@ShougoMatsuさんの実況・解説があって, ときどき「Vimだとこうですね」と間にはさんでいて面白かった.

盛り上がったのが『エディタの鉄人』で, https://www.gnu.org/software/emacs/history.html のページからEmacsのリリースリストをコピペしてきて, これに対して

  1. - を タブに変換する
  2. <li></li> で各行を囲む
  3. Markdownのテーブルにする

という操作を前で披露してもらうというもの.

操作一つをとっても一人一人でやり方が違っていて, - を複数選択してマルチカーソルでタブにする人や, replace-regex で置換する人, <li> は矩形選択して </li> は置換を使う人, マルチカーソルで <li></li> を挿入する人と様々だった.

ただMarkdownのテーブルに直す操作では, それぞれの方法で | を挿入してから見た目を整えるときにorg-modeの機能の一部をMarkdownの編集に利用する, といったものが共通していてorg-modeを全然利用していない自分としては目から鱗だった.

他にもorg-modeの凄さを感じる瞬間が多く, 他人と共有するMarkdownやPDF, docxをorg-modeで書いてから変換させたり, 発表スライドをorg-modeで作ってきている方もいてorg-mode万能説を感じた.

他人がEmacsを使う様子を見ていると自分はまだまだEmacsを活用しきれていないなと思ったけど, 今後どんな風にEmacsを拡張していくかの参考になったので他人の使う様子を見れたのは良かった.

またこのような機会があれば是非参加したいし, 今度は自分のエディタを披露できるくらいになりたいと思った良いイベントだった.

当日の様子はこちらをどうぞ. twitter.com