更新されたので beta1 から pom.xml のバージョンを書き換えてインストールしてみました。
ビルドしてみると app-cubby.dicon で cubby-handlers.dicon が存在しないと言われエラーに。どうやら cubby-s2-2.0.0-beta1.jar から取り除かれたようです。 app-cubby.dicon の以下の記述を削除。
<include path="cubby-handlers.dicon"/>
エラーを取り除いて実行。
[ESSR0046]コンポーネント(requestParsers)が見つかりません
サンプルを見てみると app-cubby.dicon が修正されていました。
<component name="multipartRequestParser" class="org.seasar.cubby.controller.impl.MultipartRequestParser" />
<component name="defaultRequestParser" class="org.seasar.cubby.controller.impl.DefaultRequestParser" />
<component name="requestParsers">
{ multipartRequestParser, defaultRequestParser }
</component>
修正して実行。アクセスしてみると別のエラーに変わりました。
java.lang.IllegalArgumentException: サービス interface org.seasar.cubby.spi.PathResolverProvider を提供するプラグインがありません
ここでようやく修正内容を確認すると(遅い!)、プラグイン機構が見直されたようです。
CubbyServlet からプラグインを初期化する仕組みになったので、 web.xml に CubbyServlet をロードしてあげるようにすることで動作するようになりました。
<servlet> <servlet-name>cubby</servlet-name> <servlet-class>org.seasar.cubby.servlet.CubbyServlet</servlet-class> <load-on-startup>2</load-on-startup> </servlet>
少しコードを追っかけてみると Cubby 内の ServiceLoader クラスが META-INF/services/org.seasar.cubby.Plugin を読みに行ってプラグインをロードする仕組みになっていました。 JDK 1.6 から搭載された ServiceLoader をエミュレートした形になっているといえます。
GW を利用して学生時代の友人たちと三重の熊野まで 2 泊 3 日で行ってきた。
携帯電話は EMOBILE を利用しているけど電波が届かない。どうみても隔離されました。本当にありがとうございました。こんなにも長い間ネットから完全に離れたのは久しぶりで、自然に囲まれ温泉に朝晩浸かることができ、ゆっくりと流れる時間のなか友人と過ごすことができた。
旅の終わりには名古屋でさらに友人と合流し飲み会。卒業以来に会う人もいて、楽しい旅行になった。
今回朝 6 時前には起きて行動したわけだけど、改めて時間を多く利用できることを実感。これから休日でも朝 9 時には起きると決意したけど、今日早速 11 時に起きた。
何はともあれリフレッシュできたのでスイッチを切り替えて、明日から早く流れる時間のなか一日を充実して過ごしていきたい。
唐突に Firebug で実行するのではなく js ファイルを JavaScript エンジンに流し込みたくなりました。 MacPorts に入っている Spidermonkey はバージョンが古いのでソースからビルドしてみました。
$ sudo port install mercurial
$ hg clone http://hg.mozilla.org/mozilla-central/
$ cd mozilla-central
$ sudo port install autoconf213
$ sudo port install libidl
$ echo '. $topsrcdir/browser/config/mozconfig' > .mozconfig
$ make -f client.mk build
$ cd dist/bin
$ ./js
js> version();
180
js> [10, 4, 3].reduce(function(pre, cur, i, ary) { return pre * cur; });
120
hg clone とすべてビルドしている make でコーヒー数杯飲めると思います。
時間を取って 1.7, 1.8 の勉強したい。
関係ないけど configure make も理解しないといけないなー。
.emacs に以下を追加。
(iswitchb-mode t) (setq iswitchb-prompt-newbuffer nil)
これまでは既存バッファを開くときは C-x C-b でバッファリストを出して選択していましたけど、 C-x b (switch-to-buffer) からインクリメンタルサーチが行えるものが標準で用意されていることを知ったので導入してみました。
iswitchb-prompt-newbuffer 変数を nil にしているのは iswitchb-mode を有効にすると、存在しないバッファを生成するときにいちいちプロンプトで問い合わされるようになってしまうため、導入前と同じ動きをするよう無効にしました。
途中まで入力していくつか絞ったところで C-x s でバッファ選択を切り替え、 RET または C-m でバッファを開けてこれは便利。
zsh の PROMPT をコマンドの戻り値で色変更するようにしていたのが原因でした。解決できないので大人しくユーザー名とホスト名を出すだけにしました。
var html = $("html");
var rect = {
"height": html.height(),
"width": html.width()
};
$("body") の場合 body の margin の影響を受けること、 IE, Opera の場合互換モードで現在表示している領域を取得してしまう問題もある*1ので $("html") で取る方向で。
ブラウザの表示領域のサイズを取得する方法。 - Enjoy*Study
[追記]
$(document) でも同じ値が取得できるので、 document のほうがよさげ。
*1 互換モードで動かすのもどうかと
よくパスワードを忘れるのですが、パスワードを再登録するやり方として 2 つの手法を見かけます。
これらの手法について深く考えたことがないので、ユーザーと開発(実装)の立場でメリット、デメリットを考えてみようと思います。
1 の場合パスワードが平文で送られるというのはデメリットな感じがしますが、 1,2 ともに POP/HTTP で受信している場合に、盗聴されていると侵入されます。ので 1 はパスワードを変更するまで、第三者にパスワードを知られる状況になっていることがデメリットになると思います。
開発する場合どういったものを実装する必要があるか考えてみます。
(組んだことがないので、もし自分が実装するのであればという話)
2 は開発コストが多くかかるのが分かります。平文のパスワードが残ってしまうリスクをどう考えるか問題はありますが、ユーザー、開発お互いの状況によって取捨選択できればよいものかなと思います。自分自身ユーザー側の立場としてパスワードを送られてくることは嫌ではありませんし、悩みどころではあるのかなと思いました。
今更すぎるけど、 Gmail のアドレスがピリオドを認識していないことを知りませんでした。
小野和俊のブログ:Gmail における .(ドット/ピリオド) と +(プラス) の扱いの不思議
でも GAE ではピリオドを認識するのでエイリアスを作成する必要があるとのこと。メール送信先としてはピリオドは無視してくれるので問題にならなさそうです。
使用可能な文字 (ユーザー名、パスワード、名前) - Google Apps ヘルプ
注: Google Apps ではピリオド (.) が認識されます。 この点は Gmail と異なります。
子供は楽しんでみられ、大人は仕事観について(悩みを持っている人であれば)再考するのではないかというディズニーアニメ。テンポよくさくさく物語が進んで惰性がまったくなく、時間も短いので気軽に見られます。ディズニーらしいベタベタな展開です。はい。
仕事に対する憧れ、やりがい、才能、居場所、チームワーク。そんなことを考えさせられました。
jQuery の bind(click とか) でロード時ではなく後からイベントを登録し、後からも何度も呼ばれる場合次々と実行する関数を追加してしまう。こうした場合リスナーを削除する必要が出てくるわけで jQuery の場合には unbind 関数で、イベント(名)と関数を渡して削除してあげる。
$("#hoge").click(function(e) {
$(this).unbind(e, arguments.caller); // $(this).unbind(e.type, arguments.caller);
alert('foo');
});
この場合 click イベントが新たに追加される前にクリックされることが前提条件にはなるけれど。。
jQuery には一度だけ実行する関数がすでに提供されていたような気がしたので調べてみると one メソッドがあった。これに置き換えるとすっきりする。
$("#hoge").one("click", function() {
alert('foo');
});
中で何が行われているか少し興味があったので one メソッドを覗いてみるとコード量が少なそうで、これぐらいなら気軽に読める。
one: function( type, data, fn ) {
var one = jQuery.event.proxy( fn || data, function(event) {
jQuery(this).unbind(event, one);
return (fn || data).apply( this, arguments );
});
return this.each(function(){
jQuery.event.add( this, type, one, fn && data);
});
},
proxy の第二引数の関数オブジェクトを返して登録する。実行時に登録した関数をアンバインドして、実際に実行する関数を遅延実行する仕組み。また登録時に each で回しているのはセレクタ指定等で複数のオブジェクトに対応するためで、あちらこちらで each が使われている。
それから fn && data って条件文にしか使えていなかったけど、 fn が定義されていたら data を渡すようにできることをコードをみて、あ、そうかと。 true/false を返すイメージがこびり付いているけど、先頭から順に評価し有効値であれば最後まで評価し、最後のオブジェクトを返す。
やっぱりコードリーディングは大事だなあ。使えることが大事でなくて、中で何が行われているか理解していく(想像できる)ことを意識していこう。
jquery.cookie.js が分かりやすかったので、勉強がてら写経しつつ自分なりに依存を取り除いたり、ロジックを変えてみました。
function cookie(name, value, options) {
function getExpires(value) {
const baseTime = 60 * 1000;
var date;
if (typeof value == "number") {
date = new Date();
date.setTime(date.getTime() + (value * baseTime));
} else if (value.toUTCString) {
date = value;
} // else error
return "; expires=" + value.toUTCString();
}
if (typeof value == "undefined") {
var kv = /(^.+?)=(.+$)/;
var space = /^\s+|\s+$/;
var cookies = document.cookie.split(";");
for (var i = 0; i < cookies.length; i++) {
var cookie = cookies[i].replace(space, "");
var match = cookie.match(kv);
if (name == match[1]) {
return decodeURIComponent(match[2]);
}
}
return null;
} else {
options = options || {};
if (value === null) {
options.expires = new Date(0);
}
var expires = options.expires ? getExpires(options.expires) : "";
var path = options.path ? "; path=" + (options.path) : "";
var domain = options.domain ? "; domain=" + (options.domain) : "";
var secure = options.secure ? "; secure" : "";
document.cookie = [name, "=", encodeURIComponent(value), expires, path, domain, secure].join("");
}
}
cookie("hoge", "foo", {"expires" : 15});
console.log(cookie("hoge"));
foo
cookie("hoge", null);
console.log(cookie("hoge"));
元のスクリプトは期限 (expires) の単位が日単位だったのですが分単位にしています。クライアント側だけで一時的に使うことを想定したためです。
日単位に戻す場合は baseTime をいじります。
const baseTime = 24 * 60 * 60 * 1000;
JavaScript では実引数を指定しない場合、仮引数には undefined が入ります。今回の cookie 関数では削除する場合は第二引数に null を明示的に渡すようになっていて、 undefined と null を効果的に使い分けた例だと言えます。
今更 cookie なのかもしれませんが、 localStorage は有効期限が指定できなかったりと用途が違うのかなと思う節があるので、 cookie はこれからも使われ続けていくでしょう。
全角英数字記号文字コード値から 65248 を引く。
CJKTokenizerの全角>半角正規化のロジック修正(2.9) | 関口宏司のLuceneブログ
でも条件として「65281以上65374以下のみ」
["b", "c", "d", "f", "g"].forEach(function(c) {
console.log(String.fromCharCode(c.charCodeAt() - 65248));
});
b c d f g
最新バージョン 0.4.2 においてキャッシュクリアが無効になっている気がしたので、ソースを少し読んでみました。以下のパッチを当てることでキャッシュがクリアされるようになると思います。
--- a/chrome/content/sbmcounter.js
+++ b/chrome/content/sbmcounter.js
@@ -467,7 +467,7 @@ var SBMCounter = {
// delete cache timer
this.config.timer.cache = setInterval(function() {
- for (var i in this.cache) {
+ for (var i in self.cache) {
if((new Date().getTime() - self.cache[i].lastDate) >=
(self.config.cacheTimer() * 60 * 1000)) {
delete self.cache[i];
}
最初の会社は借り上げ寮みたいなものだったので、実質初めて東京で一人暮らしを始めたときに購入したデスク、チェア、テーブルを処分することに。こう書くとなんだがもったいない感じがするけれど、椅子がなくなると一気に部屋が広くなる。
さすがに小さいテーブルは買うと思うけど、寝っ転がってノート PC いじられればそれでいいや。もう少し身の回りを軽くしていきたいなあ。
ここ数ヶ月前ぐらいから画面を開くと、時間が 1,2 時間遅れている現象に頻繁に出くわし、ググってみるとすでに同じ現象に合われた方がいるみたいです。
価格.com - 『時計の時間がよくずれる』 イー・モバイル S11HT (EMONSTER) のクチコミ掲示板
この中のアドバイスの一つを試してみたところ、設定して一月ぐらい経ったけど一度もずれることがなくなりました。
かれこれ腕時計をきちんとはめるようになって 1 年は経ち、携帯電話の時計を見ることはなくなっていたとはいえ致命的な問題だったので直ってよかったです。
それはそうと腕時計はしていたほうがいいですね。携帯で見るのがみっともないとかそういう話ではなく、腕につけていないとカバンからごそごそ取り出す無駄が発生します。自分だけでなく人に聞かれたときにも即答えられ気持ちいいです。
いまのところ今の時間を知りたいというゴールに対して、これ以上最適なインターフェースは思いつきません。逆に見つければお金持ち。
# ユーキさん [windowsシャツを進呈しよう]