improve functionality tests

機能が増減したわけではないのだけど、モードの移行処理をけっこう大きく書き換えた。こうやって大胆に変更できるのは、Selenium による自動テストがあるからだ。山ほど書き換えようがテストに通ればそれでおっけーなのである。

というわけでテストしたところぜんぜん通らないのでちくちくと修正した。地味な作業といえば地味なのだけど、これを行わないとリリースできない。

ところで、wasavi のコードが変更されるにつれ、テストコードも併せて進化させる必要がある。例えば wasavi 側ではキーイベントをデキューによって処理することで先行入力できるようにした。つまり、様々な理由でキー入力をブロックしている状態でもとりあえずその間に行われたキー入力を覚えておいて、ブロックが解除されたら再生するようになった。一方テストコードでは、先行入力できない前提でキーストロークを割と細かい単位で実行完了待ちのウェイトを行うようになっている。これはもはや不要だ。テスト用のキーストロークを一気にどばっと送出して構わないし、一気に送出しても正しく動作するのが想定された仕様だ。というわけでそのへんもいじった。

 * * *

式の評価を行う [cci]=[/cci] レジスタを vim から移植したわけなのだが、これはレジスタだ。ということは、ex コマンド
:put [register]
において指定することもできるはずだ。指定すると、どうなるんだろう? と vim で試してみると、式入力状態には遷移しない。単に最後に評価された結果が参照されるだけだ。ほう。なんか、一貫してない動作な気がするが、vim がそうやってるならと wasavi でもそのとおりにした。

 * * *

ググってみると、reddit で wasavi についてのストーリーが立っていたらしい。これはちょっとうれしい。個人的な感覚だけど、ソフトウェアが広く知られるにはとりあえず slashdot と reddit と hacker news で取り上げてもらうのがスタートラインなんじゃないかと思うわけです。そのうち reddit はクリアしたのだ。一方で、hacker news でも何度かストーリーが立っていたようなのだけど、どれもまったくコメントがつかないまま流れているようなのでこれはまだクリアしたとは言えない。ちなみに slashdot ではまったく wasavi の話題はない。

関係ないけれど 4chan 系とかでもたまーに wasavi が話題になっているようなのだけどググりにくいのでちょっとよくわからない。

going back and forth #4

モードの遷移についていろいろと修正した。また、サブモードを取り除いた。これにより、キー入力を実際に処理する [cci]processInput()[/cci] も大きく書き換えた。この関数ではモードに従った分岐をしつつそれぞれの処理を行うのだが、それに先立ってサブモードを捌きつつ適宜つじつまを合わせる処理をしていた。今回の修正によりそれが必要なくなった。ついでに、モードごとの処理を別の関数に分割して関数テーブルにより実行を振り分けるようにした。

going back and forth #3

vim で [cci]:help “=[/cci] することで [cci]=[/cci] レジスタの詳細な説明を得られる。

それによれば、単に四則演算式というわけではなくて、vim script の式っぽい。つまり [cci]:help expression[/cci] で見られるような感じのそれである。そして、式の結果として期待されるものの型は本質的に文字列だ。数学的な結果はむしろ異端で、型変換する必要がある。これは移植するには大規模すぎるし、また時期尚早すぎる。wasavi はスクリプティングをまだ実装していない。

算術演算に絞って言えば、四則演算以外の演算子としては

  • %: 除算の剰余

が足りないので、それは実装することにしよう。

すなわち、wasavi の [cci]=[/cci] レジスタで受け付ける式は、

expression :=
addsub := ( "+" )*
( "-" )*
muldiv := ( "*" )*
( "/" )*
( "%" )*
factor :=
"(" ")"
signed-numelic-literal :=
"+"
"-"

という文法になる。ここで [cci]numeric-literal[/cci] は、ecmascript での数値表現に準じることにする。つまり整数表現、小数点表現、指数表現、および 0x なんちゃらの形式である。

というわけで、そういうパーサを書いた。四則演算式のパーサ自体としては特に何か言うこともない素朴なものだ。

going back and forth #2

vim には特殊なレジスタ [cci]=[/cci] がある。これは本当に特殊だ。まず読み込み専用である。そして、このレジスタを指定した時点でモードが 1 行入力状態に移行する。

なにを入力すればいいのかというと、四則演算式である。式を入力すると、その計算結果がレジスタの値になる。したがって、例えば

"=99*99P

などというキーストロークによりバッファに [cci]9801[/cci] が入力される。ちょっとした電卓代わりになる。

これを wasavi に実装したい。

実装にあたっては、いろいろな角度から考えることがある:

  • 四則演算式と書いたが、他の演算子もあるかもしれない。vim のそのへんの仕様を確認する必要がある
  • 前の記事で、リテラル入力時に backspace を使えるようにした。これは四則演算式の入力もリテラル入力の一種として実装するつもりだったからで、つまり長い式を入力するために最低限それくらいはないと辛かろーということなのだが、やはり vim と同様に 1 行入力状態を挟んだほうが良いかもしれない。その方が、すでに存在する様々な編集のためのショートカットが使えるからである。特に、クリップボードから式を貼り付けたい場合にリテラル入力にもクリップボード操作の処理を実装することはない(クリップボードからの読み込みは非同期なので面倒くさいのである)
  • モードの遷移に関して、wasavi のそれはちょっと良くない実装がある。例えば、ex コマンド入力中に [cci]^R=<式>[/cci] などというキーストロークで計算結果を得たい場合、1 行入力状態からさらに 1 行入力状態に移行することになる。この時、遷移前の行の状態(内容とカーソル位置)を覚えておいたり、逆方向に遷移した場合はそれらを復帰させる必要がある。現在の wasavi の実装はそれを考慮していない
  • モードの保持に関してもうひとつ良くない実装は、モードの下にサブモードがあることだ。これはレジスタ名の入力、リテラル入力、コンソールのプロンプトなどがある。これはサブモードにする必要は本来はない。不必要に複雑になっているのでこれも併せて修正したい

going back and forth

input モードでは [cci]^V[/cci] を前置することでリテラルを入力することができるが、vim 同様、特殊なシーケンスがいくつかある

このうち、リテラル入力中に backspace が使えるようにした。

しょーもない機能追加ではあるのだけど、重要なのである。なぜなら [cci]^R =[/cci] をポートしようとしているのだが、やはり同じようなインターフェースにするからだ。

a suddenly farewell #5

とりあえず、PR-400NE は PPPoE ブリッジさせるようにしてルータ機能を切り離し、一方で別の無線 LAN のアクセスポイント(型番忘れたけど buffalo のやつ)のルータ機能を有効にした。

ひとまずやたら遅い現象はなくなった。やれやれ。

allow resizing from wasavi #2

しかしながら、やはり [cci]columns[/cci] と [cci]lines[/cci] を書き込み可能にするというのはちょっと無理のある仕様だ。たとえば端末の中で立ち上げた vi から [cci]:set lines=25[/cci] とかやっても、端末のサイズが変わるわけではない。それと同じことだ。もちろん gVim であればそういうサイズ変更もできるが、元の textarea と wasavi の関係性というのはやはり端末とその中で動く vi に近い。

そういう中で、あえてサイズ変更可能にするならば、元の textarea から wasavi へ向かっている強制力の鎖を断ち切る手段も導入する必要があるよね、ということを issue の中でまとまった。というよりも、そのへんまでしかまとまっていない。どういう仕様が正しいのかいまいち自分の中でイメージがわかない。

と入っても放置するわけにも行かないので、とりあえず組んでみた。まずオプション [cci]syncsize[/cci] を導入する。これがオンである場合、wasavi のサイズは textarea のサイズに従う。スクリプトにせよ、ウィンドウの端をユーザーが掴んだにせよ、textarea 内のリサイズハンドルをドラッグしたにせよ、何らかの理由で textarea のサイズが変更された場合、即座に wasavi のサイズもそれに追従する。[cci]columns[/cci] / [cci]lines[/cci] への書き込みは可能だが、それは textarea と wasavi のサイズを同時に変更する。

一方、[cci]syncsize[/cci] をオフにすると、[cci]columns[/cci] / [cci]lines[/cci] への書き込みによって変更されるのは wasavi のサイズだけである。

a suddenly farewell #4

それにしても、なぜ突然 ipv6 の問題が出てきたのか。と思って調べてみると、うちのルータはフレッツ光の PR-400NE だが、ファーム自動更新によって ipv6 PPPoE に対応しました的なニュースとおかしくなった日付が重なる。

うん。確かに怪しい。こいつだ。

そして、実は Windows 7 マシンも似たような現象が起きていた。こちらは Opera だけではなく、あらゆるブラウザの動作がおかしい。おかしいというか、表示までに恐ろしく時間がかかったり、タイムアウトになったり、ping がロスしまくったりする。これはつまりかつて話題になった、フレッツ光の ipv6 フォールバック問題ということなのかしらん。

はて、どうしたものか…。

allow resizing from wasavi

issue #36 への対応。

wasavi が持つオプションの中に、[cci]columns[/cci] と [cci]lines[/cci] というものがある。これは、wasavi の実行時におけるあるタイミングでの桁数(正確に言うと、wasavi のスクロール領域のピクセル幅を、選択されたフォントで文字 [cci]0[/cci] を描画した際のピクセル数で割った整数部分)、および行数(正確に言うと以下略)を示している。

そもそも、wasavi のサイズは、寄生元の textarea のサイズに依存していて、そこには明確な主従関係がある。つまりまず textarea のサイズがあり、wasavi はそれに従うのみなのである。したがって、[cci]columns[/cci] と [cci]lines[/cci] は実質的に読み込み専用であり、新たな値を上書きすることはできるが、意味を持たない。何の副作用も起こさない。

件の issue は、これを書き込み可能にして、書き込んだときはその値で wasavi のサイズを更新してほしいというものだ。これは、一見簡単そうなのだが、しかしよく考えてみると前述の主従関係を根本的に破壊する変更なのでかなり困ったのである。

しかしただ拒絶するのもどうか。textarea のサイズによらず、常に同じサイズで wasavi を起動したいという要件も確かにあり得るのだ。

a suddenly farewell #3

-debugsocket 5 で出てくるログをよく見てみると、ipv6 のアドレスに接続しようとしていてことごとく失敗している。

ということはシステムから ipv6 を切り離せばいいのか? [cci]/etc/sysctl.conf[/cci] に以下を追加:
net.ipv6.conf.all.disable_ipv6 = 1
net.ipv6.conf.default.disable_ipv6 = 1
net.ipv6.conf.lo.disable_ipv6 = 1



$ sudo sysctl -p

で、起動。
あ。動いた。
でもなんで突然こうなるのかな!