Charsbar::Note

2014/04/24

Pod::PerldocJp 0.18

リリースしたのは一週間ほど前なので見ている方はすでに見ているかとおもいますが、WEB+DB PRESS Vol.80あわせの作業として、Pod::PerldocJpに手を入れて、Pod::Perldoc 3.23に追随するようにしました。

WEB+DB PRESSの原稿を書き始める前と比べると、大きな変更点が2つあります。

-Jオプションをつけなくても日本語が表示されるようにしました。

perldocjpコマンドの中で-Jオプションを強制するようにしたので、perldocjp <ドキュメント名>だけで(あれば)日本語ドキュメントを表示できます。

perlvarやperlfuncのように、-a オプションでperlapiの各項目を切り出せるようになっています。

最近本家に追加された機能なのですが、XSを触る人には地味に便利だとおもいます。そしてこんなマイナーなドキュメントまで翻訳があったことにただただ感謝。

2014/04/21

WEB+DB PRESS Vol.80

4月24日発売のWEB+DB PRESS Vol.80に、Perl Hackers Hub連載の第26回として「Perlで困ったときの調べ方」という記事を書きました。

最初に「新入社員の人に見てもらいたいもの」というお題をいただいたときは何を書こうかと迷ったのですが、やはり一番は

ということだよなあというわけで、perldocの使い方を中心に、自分が日頃困ったときの情報源としてよく利用しているもろもろについて、ざっくりまとめてあります。

perldocについては過去にcho45さんもPerl Hackers Hub連載第14回で記事を書かれていますし、私自身、モダンPerl連載の第5回でまとめたことがあるのですが、これらの単なる焼き直しに終わらないよう工夫してみました(過去記事の落ち穂拾いをしたともいう)。

他の方の記事では、Vol.80の特集3「はじめてのMac開発環境」の第2章、第3章(Fukuoka.pmなどでお世話になっているヌーラボの中村知成氏の記事)にも今回の記事と関係の深い内容が書かれています。

すでに先行販売されているところもあるようですが、店頭などで見かけた際にはお手にとっていただければ幸いです。

2014/04/07

Test::PAUSE::Permissions

たまに、そう、CPANディストリビューションの割合からすると1%ほどのことではあるのですが、他の人からモジュールを引き継いだときに必要なパーミッションを全部もらえていなかったとか、名前がかぶっているのに気づかなかったとかで、PAUSEの索引に登録してもらえないディストリビューションが生まれてしまうことがあります。

そういう問題を防ぐにはリリース前にPAUSEのパーミッションの確認しておくに限る、というわけで、Test::PAUSE::Permissionsというモジュールをリリースしました。

基本的な使い方は、SYNOPSISに書いてある通り、xt/perms.tのようなテストファイルにこう書いておくだけ。

use strict;
use warnings;
use Test::PAUSE::Permissions;

all_permissions_ok();

リリース時に(環境変数RELEASE_TESTINGを有効にして)このテストを実行すると、ディストリビューション内のpackageを抽出し、CPANからパーミッションの索引をダウンロードしてきて、それぞれのpackageについて、パーミッションの状況を確認します。持ち主が登録されていない(誰もそのpackageを登録したことがない)か、持ち主に自分が含まれていればテストが通りますし、自分がパーミッションを持っていないpackageが含まれていたらテストが失敗するので、パーミッションの持ち主に連絡して必要なパーミッションをもらうか、package名がかぶっている場合はお手元のpackageを修正する、あるいはMETAファイルの設定にno_indexを追加して索引に登録されないようにする、等の手段を講じてください。

Test::PAUSE::Permissionsは、METAファイル内のx_authorityというフィールドの値があればそこからリリースする作者のPAUSE IDを取得します。また、各.pmファイルに $AUTHORITYという変数が指定されていればそこからIDを取得します。どちらもない場合、モジュールのリリースにCPAN::Uploaderなどを使っている方ならホームディレクトリに.pauseという設定ファイルがあると思いますが、そこからIDを取得します。それすらもない場合は、テストをスキップします。また、このテストをツールなどで自動生成する場合は、all_permissions_ok()の引数としてPAUSE IDを渡してやれば、.pauseにそのIDが登録されているかのように振る舞います(ただし、ここで渡したIDよりも、x_authorityおよび$AUTHORITYの指定の方が優先されます)

修正: miyagawaさんにご指摘いただいて、0.04からはx_authority等をテストの対象に含めるのをやめました。情報自体は取得しますが、テストは.pause (およびall_permissions_ok()の引数)で指定されたPAUSE IDに対してのみ行います。

2014/03/24

Perl QA Hackathon 2014に参加してきました

今回は特に予告を書きませんでしたが、昨年、一昨年に続き、今年も3月13日から16日までフランスのリヨンで開催されたQA Hackathonに参加してきました。すでに多くの方がまとめ記事を書かれているので詳細はそちらをご覧いただくとして、今年は、昨年ランカスターで議論したことを肉付けしてPAUSEなどの実装に落とし込むという位置づけの年だったこともあり、細かい点で突っ込んだ議論は多々あったものの、昨年のように「ここがこう変わるから注意してください」とみなさんに報告しておかなければならないことはなかったかと思います(古いディストリビューションなど最近のベタープラクティスにしたがっていないディストリビューションをアップロードする際に多少の注意が必要になったことや、package NAME BLOCKの形式が正しくPAUSEに認識されるようになったことなど、細々とした挙動の変化はありますが、これは重箱の隅をつつくような話でしょう)。

私もおおむねその流れにしたがって、CPANTSにPAUSEのパーミッションまわりの情報を組み込んでみたり(まだ不完全ですが、no_unauthorized_packagesというメトリクスを追加しています)、PAUSEの問題点を修正したりしていました。また、Neil Bowers氏のCPAN Dashboardをはじめとする一連の統計情報についての情報交換をしたり、マーケティングの一環?としてのCPANを256倍楽しめるようにする方法みたいな話を横で聞いたり、DBD::SQLiteについてのやりとりもありました。もっと話をしてくればよかったなあと思うことは多々ありますし、ネットワークにつながらなくて往生したとか、活動時間があわなくて苦労したとかもありましたが、プライベートも含めて、充実したハッカソンであったことです。あらためて主催・運営にあたった方々とスポンサー各社に感謝します。

以下、公開私信。

  • 夕食時にmoznion氏のGrantの件が話題になっていました。コメント欄にもある通り、好意的な意見が多くてほっとしたことです(半分くらいはHackathonの参加者からのコメントです)。
  • 具体的な話まではしてきませんでしたが、CPAN Testersのミラーの件、日本に置きたいなら手伝うし、いい考えだと思う、とは言ってもらっています。
  • 口頭では紹介したことがあるような気もしますが、http://cpan.cpanauthors.org/ はいわゆるリアルタイムミラーです。スペックはともかく国内の専用サーバでホストしていますので、CPAN Testersのサイトなどでは遠くて遅い、という方はお試しくださいませ。
  • 来年はベルリンだそうですよ。

2013/12/24

MojoliciousとWebSocketとiTunesと

これはMojolicious Advent Calendar 24日目の記事です。

iTunesに英語教材などを放り込んでエンドレス再生していると、「ここにテキストが表示されていればいいのになあ」と思うことがあります。あるいは、洋楽を流しっぱなしにしているときに、ふと聞き取れなかった歌詞を確認したくなるとか。

もちろんその都度メモなりなんなりを開いてもいいのですが、いちいち該当のトラックに関係のあるファイルを探すのも面倒ですから、トラックが変わるたびに自動でテキストが表示されるようにしたいものです。GUIをごりごり書くのは面倒ですし、ターミナルに流し続けるのも見づらいですから、ここはテキストはブラウザに表示することにし、WebSocket経由で更新し続けるようにしてみましょう。

Windows環境では以下のようにWin32::OLEを利用することでiTunesからトラック情報を取得できます(Mac環境の場合はCPANにMac::iTunesというモジュールがあるようですので、適宜読み替えてください)。

use Win32::OLE;

my $itunes = Win32::OLE->new('iTunes.Application');
my $track = $itunes->CurrentTrack;
my $name = $track->Name;
my $album = $track->Album;
my $path = $track->Location;

Mojoliciousには特定の処理を繰り返す仕組みが用意されていますので、ここではそれを利用して、毎秒iTunesのカレントトラックを確認し、変更があったら関連するテキストファイルを読み込むことにしましょう。

use Mojolicious::Lite;
use Mojo::Asset::File;
use Mojo::IOLoop;
use File::Basename;

my $current;
Mojo::IOLoop->recurring(1 => sub {
  my $track = $itunes->CurrentTrack or return;
  if (!$current or $current ne $track->Name) {
    $current = $track->Name;
    my $album = $track->Album;
    my $basename = basename($track->Location);
    $basename =~ s/\.m4a$/.txt/;
    my $textfile = app->home->rel_file("text/$album/$basename");
    my $text = Mojo::Asset::File->new(path => $textfile)->slurp;

  }
});

続いて、WebSocketまわりの処理を実装します。ここではWebSocketの接続を%clientsという変数に保存して、あとでループの中から利用できるようにしています。

use Mojolicious::Lite;

get '/' => 'index';

my %clients;
websocket '/connect' => sub {
  my $self = shift;
  my $id = "".$self->tx;
  $clients{$id} = $self->tx;

  $self->on(finish => sub {
    delete $clients{$id};
  });
};

app->start;

あとはループの中で、更新された情報をJSONにくるんで送り出してやり(cp932でdecodeしているのはもちろんWindows環境だからです)、

use Mojo::ByteStream 'b';
use Mojo::JSON 'j';

Mojo::IOLoop->recurring(1 => sub {
  if (!$current or $current ne $track->Name) {
    ...
    my $text = Mojo::Asset::File->new(path => $textfile)->slurp;

    my $json = b(j({
      title => b($current)->decode('cp932'),
      text => b($text)->decode('cp932'),
    }))->decode;
    $clients{$_}->send($json) for keys %clients;
  }
});

その情報をJavaScriptで画面に書き出してあげれば完成です。

@@ index.html.ep
<html>
<head>
%= javascript '/mojo/jquery/jquery.js';
%= javascript begin
$(function(){
  var ws = new WebSocket('<%= url_for('connect')->to_abs %>');
  ws.onmessage = function(msg) {
    var res = JSON.parse(msg.data);
    $('.title').text(res.title);
    $('.text').text(res.text);
  };
});
% end
</head>
<body>
<h1 class="title"></h1>
<pre class="text"></pre>
</body>
</html>

このようなWebSocketを使ったMojolicious::Liteアプリは、ChromeなどWebSocket対応のブラウザでないと正しく動作しませんし、現状ではplackupも、Windows環境の場合はhypnotoadはもちろん、morboさえも使えない(perl myapp.pl daemonならOK)という、なかなか厳しい制約はありますが、WebSocketを使うと、手元のブラウザだけでなく、ネットワーク上の他のブラウザでも同じ内容を表示させられますので、表示する内容を工夫すればなかなかおもしろいこともできそうです。

全体像は https://github.com/charsbar/lyrics_viewer_win32 からどうぞ。