のはずが、起きたのは9時くらい。ゆるゆると朝からトンカツと砂肝を食べ、掃除開始。
アフタヌーンの未読を消化。結構読んでない部分が多くて、2002年9月号から読み初めて11月号まで消化するのがやっと。
サンシャイン劇場で「笑いの神様3」を観てきた。目当ては「鉄拳」と「エスパー伊東」。鉄拳は期待通りの面白さで良かった。エスパー伊東は、期待通りの外し方でこれまたよかった。
でも、一番は「ちむりん」だったかな。
「こだわりのパリパリ昆布」を購入。
というわけで、Pro 版をレジストした。気になる「Full support for X11」だけど、確かに旧バージョンよりも良くなっている。
旧バージョンでは「キーボードでページ切り替え → マウスで X11 アプリをクリック → キーボードで X11 アプリを操作」という手順を踏まねばならなかったのだが、新バージョンでは、「キーボードでページ切り替え → キーボードで X11 アプリを操作」というようにマウスを使わずに済むようになった。
あと、Pro 版だけに存在する「Auto Hide」機能がいいな。ページャが邪魔にならないし、なによりニュルっと出たり入ったりするギミックが楽しい。
出遅れた感があるけど、吉野家で一日だけ牛丼が復活するそうだ。2月11日って平日じゃねーのか?と思ったら、祝日なのね。これなら並べるわ。
昨日、起動しなかったサーバを調べに現地入り。モニタを繋いで見てみれば、、、「キーボード繋がってないんですけど」(意訳)というサーバからのメッセージが。。。
そうか、そうだよね、繋げてなかったよね、、、と呟きながらキーボードを接続しリブート。さっさとBIOSの設定を変えて、キーボードが接続されてなくてもアラートを出さないようにした。
つーか、1Uサーバなんだからさ、デフォルトで外しとけよ!>キーボードアラート
1月31日の午後9時25分前後に「頻繁にニュースで見掛けるので餃子が食べたくなった。」というツブヤキと 近所の上海餃子を無性に食べたいな、と。焼と水両方行きたいなと。」というツブヤキが連発で出てきて、思わず笑ってしまった。
で、そのおかげで(?)、今日は餃子の都であるところの宇都宮まで来てみたよ。自宅を出て、首都高経由東北自動車道利用で約2時間ほど。意外と近いんだな、宇都宮。
あんまり調べずに来てしまったので有名店の場所も分からん、、、と思っていたら、長崎屋宇都宮店の地下に「宇都宮餃子 来らっせ」という、いろんな餃子店舗が集まっているテーマパーク的施設があるのを知った。ということで、この施設で食べてみたよ。
まずは「宇都宮みんみん」の「焼餃子」。これはオーソドックスな餃子。イイ感じのコゲ具合の皮はカリカリ。でも中はジューシーで美味しかった。6個で220円は激安。
次も「宇都宮みんみん」で、こちらは「水餃子」。先ほどのカリカリとは違ってツルツルとした食感が楽しい。焼餃子を食べ続けて、ちょっと油っぽくなった口の中を水餃子のさっぱりさで緩和できた。こっちも6個で220円。大丈夫なの?こんなに安くて。
まだまだお腹は余裕だったので、続いて「めんめん」の「ゆで餃子のおろしポン酢」。水餃子じゃなくて、ゆで餃子の所以は、お湯から出しているところなのか?などと考えながら待っていて、出てきたのがコレ。これはヤバイ。うま過ぎて、一気に6個を食いきってしまった。380円。
そろそろお腹もいい感じにふくれてきたのだけれど、別のエリアにもお店があったのでメニューを眺めていたところ、何やら怪しげな「餃子カレー丼」を発見。これは食わねばなるまい!と店に入った。
しかーし、これはイマイチ。この状態で出てきても、餃子は餃子で食べるし、カレーはカレーで食べる。一緒になっているメリットがない。カレーは「ひと味抜けたボンカレー」みたいな感じで美味しいとは言い難い。300円なので安いっちゃ安いんだけど、盛りはごはん茶碗だし、他の餃子の美味しさと比較してしまうとリーズナブルとは言い難いかな。
もう一品、一緒に頼んだのが「青源」の「水餃子」。味噌味のスープにちょっと酸味が入っていたのだが、もうちょっと酸味が強くても良いかなと思った。あと味噌も濃い方がオレの好み。420円。
今日、食べた中では「ゆで餃子のおろしポン酢」が一番美味しかったし、リピートしたくなる味だったなぁ。
で、今日は宇都宮に泊まる事にしたんだけど、、、明日は雪だとか。初めての雪の中での運転が宇都宮からの帰宅ルートになるとは。。。
PSYCHO-PASS 第15話「硫黄降る街」より気になったセリフをメモ。
ストーリーのネタバレじゃないけど、これから見る予定の人は読まない方がいいかも。
「ダウンロードしておきます」
「紙の本を買いなよ、電子書籍は味気ない」
「そういうもんですかねぇ」
「本はね、ただ文字を読むんじゃない。自分の感覚を調整するためのツールでもある」
「調整?」
「調子の悪い時に本の内容が頭に入ってこない時がある。そういう時は何が読書の邪魔をしているか考える。調子が悪い時でもスラスラと内容が入ってくる本もある。なぜそうなのか考える。精神的な調律、チューニングみたいなものかな。調律する際、大事なのは、紙に指で触れている感覚や、本をペラペラめくったとき瞬間的に脳の神経を刺激するものだ」
<body>
タグすら存在しない
GitHub で Watch している、とあるプロジェクトの通知メール(Notification Mail)を Gmail で受信してるんだけど、いきなりモアイ画像だけのものが出てきた。
Gmail にケータイキャリアからメールを送ると絵文字が表示されるのは知ってたけど、GitHub の絵文字にも対応したのか!?と思って、「メッセージのソースを表示」で生のデータを見てみたら、最初に目に入ったのが : moyai : の文字だった。
(実際は : と moyai と : の間のスペースは無い。tDiary でも絵文字が出るので抑制するため)
えー! Gmail で : moyai : と送れば絵文字変換されんの!?と思って自分宛に送ってみたけど、変換はされなかった。
もう一度、生のデータをみたら、マルチパートで HTML も送られて来ており、こちらにモアイ画像の <img>
タグが入っていたので、それが表示されていたというオチ。慌てるの良くない。
そこで気になったのが、HTML パート内の構造。<html>
タグも <body>
タグも存在せず、いきなり <p>
で始まっている。
まぁ、これでも実際に表示されているし、問題ないっちゃないんだけど、HTML 構造的には Valid じゃない気もするので、若干気持ち悪いなーとか思ったりした。
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: 7bit
<p><img class="emoji" title=": moyai :" alt=": moyai :"
src="https://a248.e.akamai.net/assets.github.com/images/icons/emoji/moyai.png"
height="20" width="20" align="absmiddle"></p>
<p style="font-size:small;-webkit-text-size-adjust:none;color:#666;">
—<br>
Reply to this email directly or
<a href='https://github.com/tdiary/tdiary-core/issues/255#issuecomment-13027488'>
view it on GitHub</a>.
</p>
<img src='https://github.com/notifications/beacon/DUMMY.gif'
height='1' width='1'>
(見やすいように適当に改行を入れている)
ソースを見て分かるのは、GitHub の絵文字は Akamai に置かれていること。これは Web での表示も同様だった。
あと、通知メールが開封されたかどうかをチェックしてるみたいだね。
<img src='https://github.com/notifications/beacon/DUMMY.gif' ...>
の DUMMY の部分は、実際には64文字の文字列が入っていた。たぶんユーザ毎に違う文字列だと思われる。何よりパスに beacon って入っているし。
ついでに気になったので、Gmail から送信される HTML パートの形式はどうなっているのか見てみた。
Content-Type: text/html; charset=ISO-8859-1
<img src="cid:000@goomoji.gmail"
style="margin: 0px 0.2ex; vertical-align: middle;" goomoji="000">
こちらも <html>
も <body>
も存在しない。
もしかして、他のところもだいぶ入ってない感じ?
今回、やりたいことは、ちょっと前の日記にも書いたけど、こんな内容のことを実施したいと思っている。
今更この程度のことかよ!?という内容かも知れないけど、この程度のことができないのも事実なので、淡々と学んでいくしかない。
現在は手動で次のようなコマンドを入力(もちろん履歴とか使うけど)して PHPUnit のテストを実行している。
% phpunit -c phpunit.xml [対象のテストファイル]
phpunit.xml
は、コンフィグファイルであり、普段使う設定が書き込まれている。その設定では、プロジェクト内の全てのテストを実行が指定されている。必ずしも -c
オプションでコンフィグを指定する必要はないのだけど、複数の設定ファイルを使い分けている関係で常用している。
ひとつのテストメソッドをちょっとして修正の動作確認をしたい場合には、全テストはちょっと大げさかつ効率が悪い。ファイル名を引数として渡すことで「いま修正しているファイル」を対象にテスト実行をしている。
更に実行時間を短くしたい場合には、--filter
オプションに修正中のテストメソッド名を指定して、実行対象メソッドも限定しているのだが、今回の「ファイル変更の監視」だと、修正中のメソッドまでは把握できなさそうなので、いったん置いておく。
この記事用に作ったサンプル用の PHPUnit 環境はこんな感じにしている。
% ls -1
composer.json
composer.lock
composer.phar*
phpunit.xml
tests/
vendor/
PHPUnit は Composer を使ってインストール。composer.json
の中身はこれだけ。
% cat composer.json
{
"require": {
"phpunit/phpunit": "3.7.*"
}
}
テストファイルはこんな風にしてみた。
% ls -1
fugaTest.php
hogeTest.php
それぞれのテスト内容は、ダミーなので、とりあえず絶対成功するヤツを書いている。
% cat tests/fugaTest.php
<?php
class FugaTest extends PHPUnit_Framework_TestCase
{
public function testDummy1()
{
$this->assertFalse(false);
}
}
% cat tests/hogeTest.php
<?php
class HogeTest extends PHPUnit_Framework_TestCase
{
public function testDummy2()
{
$this->assertTrue(true);
}
}
これを実行すると、「OK」になる。これで全てのテストが成功している状態。
% ./vendor/bin/phpunit -c phpunit.xml
PHPUnit 3.7.29 by Sebastian Bergmann.
Configuration read from /Users/suzuki/work/grunt/phpunit.xml
..
Time: 36 ms, Memory: 2.50Mb
OK (2 tests, 2 assertions)
さて、ここから本題。
まず npm init
を使って、package.json ファイルを作成してみた。
% npm init
いろいろと質問されてくるので、適当に答えつつ出来上がった package.json の中身はこんな感じ。いろいろ適当なのだけど、とりあえずローカルで使うだけなので、まぁ、いいか、と。
{
"name": "phpunit-watch",
"version": "0.0.0",
"description": "PHPUnit test watch",
"main": "index.js",
"directories": {
"test": "tests"
},
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "BSD-2-Clause"
}
次に Grunt 関連のインストール。grunt-cli
、grunt-contrib-watch
、grunt-phpunit
の3つのパッケージを指定してみる。grunt-contrib-watch
と grunt-phpunit
は npm のパッケージであると同時に、Grunt のプラグインという位置付けでもある。
% npm install grunt-cli grunt-contrib-watch grunt-phpunit --save-dev
--save-dev
オプションを付けると、インストールしたパッケージを package.json
へ記録してくれるそうだ。
{
"name": "phpunit-watch",
"version": "0.0.0",
"description": "PHPUnit test watch",
"main": "index.js",
"directories": {
"test": "tests"
},
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "BSD-2-Clause",
"devDependencies": {
"grunt-phpunit": "~0.3.2",
"grunt-cli": "~0.1.13",
"grunt": "~0.4.2",
"grunt-contrib-watch": "~0.5.3"
}
}
確かに devDependencies
に追記されている。
また、install
したパッケージは、node_modules
ディレクトリ以下にインストールされているのが分かる。
% ls -1
composer.json
composer.lock
composer.phar*
node_modules/
package.json
phpunit.xml
tests/
vendor/
node_modules
% ls -1 node_modules/
grunt/
grunt-cli/
grunt-contrib-watch/
grunt-phpunit/
必要なパッケージのインストールが終わったら、今後は実行用の設定に入る。設定は Gruntfile
という名前のファイルに記述する。JavaScript 版の Gruntfile.js
と CoffeeScript 版の Gruntfile.coffee
が利用できる。
grunt
コマンドの設定ファイル Gruntfile
は、make
コマンドに対する Makefile
のような存在だと思えばピッタリくる模様。
まずは、grunt
コマンドで PHPUnit の実行ができるように設定を書く。今回は、JavaScript 版の Gruntfile.js
にした。
module.exports = function(grunt) {
grunt.initConfig({
phpunit: {
classes: {
dir: './tests/'
},
options: {
bin: './vendor/bin/phpunit',
configuration: './phpunit.xml'
}
}
});
// パッケージの読み込み
grunt.loadNpmTasks('grunt-contrib-watch');
grunt.loadNpmTasks('grunt-phpunit');
}
phpunit:
以下に書いてある設定が grunt-phpunit のもの。ここでは、テスト対象のクラスを指定している classes:
と options:
を利用している。
classes:
の dir:
でテスト対象のディレクトリを指定するようだ。phpunit.xml
の中でもテスト対象を指定しているのでダブってしまうのだけど、ここはそういうものとして利用する。
options:
の内容は、PHPUnit のコマンドラインオプションと対比してあるようなので、マニュアルとにらめっこすれば、意味が分かると思う。
この状態で grunt
コマンドにタスク名 phpunit
を指定して実行すると、PHPUnit が走って、先ほどの結果と同じ出力を得られる。
% ./node_modules/.bin/grunt phpunit
Running "phpunit:classes" (phpunit) task
Starting phpunit (target: classes) in tests/
PHPUnit 3.7.29 by Sebastian Bergmann.
Configuration read from /Users/suzuki/work/grunt/phpunit.xml
..
Time: 18 ms, Memory: 2.50Mb
OK (2 tests, 2 assertions)
Done, without errors.
今度は最終目的である「ファイルの変更を監視」をする設定を書く。これは grunt-contrib-watch で実現できた。
module.exports = function(grunt) {
grunt.initConfig({
phpunit: {
classes: {
dir: './tests/'
},
options: {
bin: './vendor/bin/phpunit',
configuration: './phpunit.xml'
}
},
watch: {
scripts: {
// 監視対象のファイル
files: ['./tests/*Test.php'],
// 変更を検知した時に実行するタスク
tasks: ['phpunit'],
options: {
spawn: false,
}
}
}
});
// watch イベントが発生したら、phpunit: classes: dir: の値を動的に変更
grunt.event.on('watch', function(action, filepath, target) {
grunt.config(['phpunit', 'classes', 'dir'], filepath);
});
// パッケージの読み込み
grunt.loadNpmTasks('grunt-contrib-watch');
grunt.loadNpmTasks('grunt-phpunit');
}
追記したのは、watch: { ... }
のブロックと grunt.event.on('watch', ... });
のブロック。
watch: { ... }
内で、監視対象のファイルと、変更のあった場合に実行するタスクに phpunit
タスクを指定している。これだけの指定でも、「監視対象のファイルが更新されたら phpunit
タスクを実行する」ということなら実現できる。
でも、いまやりたいのは、「修正(更新)したファイルだけを対象にしたい」ということなので、もうひと工夫しているのが、grunt.event.on('watch', ... });
のブロック。
上記のように書くと、watch
イベントが発生した場合に、phpunit
タスクの classes:
、dir:
を設定しなおしてくれるようだ。つまり、テスト対象のディレクトリ(ファイル)の設定を「変更のあったファイル(filepath
)」としてくれるのだ。
その動的な設定変更の後で phpunit
タスクが実行されるので、目的であった「修正(変更)があったテストファイルのみテスト実行する」がこれで実現できる。
では、実行してみよう。
監視するには、引数にタスク名 watch
を付けて grunt
を起動する。
% ./node_modules/.bin/grunt watch
Running "watch" task
Waiting...
この状態で、エディタでテストケースを修正すると、その変更を検知して、phpunit
タスクを実行してくれる。
例えば、fugaTest.php
ファイルを更新してみよう。
<?php
class FugaTest extends PHPUnit_Framework_TestCase
{
public function testDummy1()
{
$this->assertFalse(false);
$this->assertTrue(true); // このアサーションを追加
}
}
すると、先ほど watch
状態になっていたコンソールには、このような出力が出た。
% ./node_modules/.bin/grunt watch
Running "watch" task
Waiting...OK
>> File "tests/fugaTest.php" changed.
Running "phpunit:classes" (phpunit) task
Starting phpunit (target: classes) in tests/fugaTest.php
PHPUnit 3.7.29 by Sebastian Bergmann.
Configuration read from /Users/suzuki/work/grunt/phpunit.xml
.
Time: 16 ms, Memory: 2.50Mb
OK (1 test, 2 assertions)
Running "watch" task
Completed in 0.108s at Sun Feb 02 2014 16: 18 :07 GMT+0900 (JST) - Waiting...
ファイルの変更が検知され、
>> File "tests/fugaTest.php" changed.
そのファイルを対象に実行されている様子が見える。
Starting phpunit (target: classes) in tests/fugaTest.php
実際に使う場合のシナリオは、ひとつのコンソールで grunt watch
させた状態で置いておき、その隣でエディタを使ってテストケースを編集・保存、テストの結果を見つつ、更に修正という形になるかな。
今回の Grunt 関連のまとめ。
なお、Grunt のプラグインには、シェルコマンドを実行するgrunt-shell もあったので、こちらを使えば専用プラグインが用意されていない場合でも好きなことができそうだ。
これで Grunt の使い方の第一歩は把握できたので、仕事なりその他なりで活用していきたいと思う。
【追記】
「ファイルを監視してタスクを実行する」なら Guard や watchr でもいいんじゃないか?的なコメント(?)を貰った。
今回は「Grunt 勉強しなきゃ → おや、watch
なんてできるんだ → おや、phpunit
のプラグインもあるんだ」という流れがあったので、Grunt 以外の実現方法を調べようという考えには至らず、それらの存在に気がついていなかったという。。。
watchr とかの記事をググると、2011年ころの記事が多くヒットしたりして、自分の技術とか知識とかがいかに遅れているかという実感を得ちゃうねぇ。。。がんばろ。
なんかふと思い立って、オレオレ Emacs Formula に Travis CI の設定をしてみた。Emacs の HEAD にinline-patchを当ててコンパイルできるかどうかのチェックをする感じにした。
どうせなら、定期的に最新の Emacs でコンパイルが通るかどうかをチェックしておきたいので、「ニフティクラウドタイマーを使ってTravis CIのビルドを定期的に実行する」を参考にして、ビルドを kick するスクリプトを作って cron で回すようにした。
#!/bin/sh
TOKEN='YOUR_TRAVIS_TOKEN_HERE'
USER='suzuki'
REPOSITORY='homebrew-emacs'
BODY='{"request": {"branch": "master"}}'
curl -s -X POST \
-H "Host: api.travis-ci.org" \
-H "Accept: application/vnd.travis-ci.2+json" \
-H "Content-Type: application/json" \
-H "Travis-API-Version: 3" \
-H "Authorization: token $TOKEN" \
-d "$BODY" \
https://api.travis-ci.org/repo/$USER%2f$REPOSITORY/requests
参考にしたページのサンプルの URL に「%2f」という記述があったんだけど、「"%2f" って "/" のことだよな?」という無駄知識が出てきたので変更して叩いたらうまく動かなかった。上記のスクリプトの例で言えば「$USER%2f$REPOSITORY
」の「%2f」は、そのまま「%2f」にしておく必要があった。
これで最新の Emacs に inline-patch がうまく当たるかどうか確認できるので、いつでも安心して最新版の Emacs を Homebrew でインストールすることができるようになった(はず)。
レアジョブの無料体験枠があと1回分あったはずだけど、法人会員がスタートしたらそれは消えた。まぁ、そういうものなのかも知れない。
今回からはカリキュラムに従って進む感じに。「初級」の中にある「ビジネススターター レベル 3」からスタートした。読む分には簡単な英語なのだけど、「説明してください」とかって設問の回答を話そうとすると途端にダメ。
予習した時に、いくつか文章を作っておいたので、それを使ってなんとかなったところもある。でも、その回答が質問とマッチしていなかった時に、先生から再質問をされると、うまく答えられなかった。リスニングもいまひとつなので、何を言っているかがふわふわしていたし、頭の中に日本語が浮かんでもそれを英語で答えることができなかった。
あと、レッスンが終わったあとの先生からのフィードバックで「ちょっとナーバスでしたね」みたいな言葉があった。そうなのよね、緊張もさることながら、まだちょっと気が引けてる感があるのは、自分でも感じている。これは慣れなのかなー。まぁ、ビビりながらも続けてみよう。
手元では、少し前から2つのバージョンの Elasticsearch を立ち上げるようにしていたのだけど、それをそのまま master へ push した。「2つのバージョン」とは v2.4 系と latest (今だと v5.2)系。
Crowi を起動するときに、 ELASTICSEARCH_URI=localhost:9200
とすれば latest に、 ELASTICSEARCH_URI=localhost:9201
とすれば v2.4 に繋がる。
▽ いし [戸塚ではえらい積もりっぷり。高速道路もそちこち通行止めだが…。宇都宮は果たして?]
▽ すずき [なんとか帰り着きましたよw]