2005年11月10日

PHP用MVCフレームワーク Mojavi

今までWebアプリ系のことは書いてなかったけど、よく忘れてしまうので一緒書いていくことにした。


確か去年の終わりごろのこと、PHPで実際に組んだことがなかったというのもあり、ゴリゴリ書いていた。
HTMLの中にソースが埋め込めるのはやっぱりいいなぁと、両方ごちゃまぜでほいほい書いていた。
その内見辛くなってきて、別ファイルに分離したり、ソースを分けたりして対処していた。
また、後になってわかってきた出力のバッファリングやセッションの機能など追加していくが、全てのページで同じようにしたかどうか調べたりが大変になってきて、ほとんどを書き換えた方が良さそうだという結論に達していたが、しばらく放置していた。

何とかせねばと重い腰をあげ、昨夜寝る前にPHP実用プログラミングSmartyの項を読んだ。
Smartyのみを使うようにしても、HTMLとPHPが分離されるので綺麗になるだろうが、どうせならMVCのフレームワークを使おうと言うことで、Mojaviについて今日調べた。
このMojaviの解説ページがわかりやすい。
Mojaviすごい。
こいつは楽チンだ。

もう一つの選択肢として、XOOPSのカスタマイズ&拡張を考えていた。
ユーザーの登録や認証機能、豊富なモジュールが初めからあるのはかなり魅力的だ。
また、インストールは驚くほど簡単に出来る。
だけど、モジュールを作るのが面倒臭そうだ。
XOOPSの仕様にあわせて作らないといけない。
また、今のものではユーザーの登録情報はそんなに必要ない。
Mojaviを使って書き換えていくことにするかな。

投稿者 Takenori : 01:50 | トラックバック

動的書き換え

Mojaviに書き換えようと決めたが、当面自分しか使わない登録用ページはそんなに急に書き換えなくても特に問題ない。
だけど、複数のページ遷移を一つにまとめ、出来るだけ少ない操作で登録が出来るように時々改良している。
そして、最近ももっと入力ステップを減らせるのではないか? といろいろと検討していて、一部HTMLを動的に変更しつつ、フレームに分割すれば入力の手間がかなり減りそうだと気付いた。

そこで動的に選択項目を書き換えるべくググっていたら、Ajaxのページがヒット。
読んでみるとやることはGreasemonkeyのスクリプトと同じようなもんか。
Greasemonkeyのスクリプトは以前少し書いた。
が、普通のページはidつけてないのでGreasemonkeyで書き換えるには面倒な処理が必要で、ある程度で止めてしまっていた。
でも、Ajaxなら自分でHTMLを書くのでidを付けられ、楽に動的にHPを変更できる。

選択項目を追加したり削除したりするだけでも事足りたのかもしれないが、Ajaxでやるようにdocument.getElementById().innerHTML=htm;てな感じでソースを書き換えることにした。
でも、JavaScriptのクラスの作り方は少し違和感がある。
JavaScriptでクラスを作ったことは今までなく、今回始めて作ってみたが…… クラスを関数定義と同じように書くとはな。
そう言えば、perlでクラスを作った時も違和感を覚えたような。
ま、それはともかく動的に切り替わるようになっていい感じだ。
DBとのやりとりにはXMLを使って、全体的にAjaxちっくにしたい衝動にかられるが、今回のでは全然そんなの必要ない。
他のところは普通のページ遷移で事足りる。

今回作ったソースは、PHPとJavaScriptとHTMLとSQLが入り乱れ。
PHPとJavaScriptが混じっているところはちょっとわかりづらい。
でも、なんか楽しい。

投稿者 Takenori : 02:33 | トラックバック

2006年02月16日

グループウェアを作ろう

グループウェアは前々から欲しくて、phpGroupWareを試したこともあるが、phpGroupWareはイマイチだった。
後、XOOPSも試してみたがどうもしっくりこない。
そこで、Webサービスクラスターにも書いたように、自分で作ることにした。

自分が最も望むことは、公開範囲を自由に細かく指定できること。
ウェブ上全体に公開、自分のみが閲覧可能、グループを指定して公開などなど。
グループは、全体に存在するもの以外に、自分ローカルだけのものも定義可能で、そのグループを使って範囲を指定することも出来るのが良い。
これが出来るのが前提条件。

なぜこのようなものが自分にとって重要かと言うと、このブログや日記、ローカルのメモなど複数箇所に文書が散らばっているのを何とかしたい。
これらを1箇所にまとめられ、一気に検索が出来たらかなり楽だ。
ここに書いたっけ? あれ? こっちだったかな? などと探すのが面倒なのだ。
まあ、いくら制限をかけるとはいえ、オンライン上にある以上漏洩してしまうこともないとは言えないが、パスワードや銀行の暗証番号など洩れるとヤバイものはそんなところには書かないので大丈夫だろう。
最大限注意は払うし。

最低限欲しい機能は、メッセージ、日報(ブログ,メモ)、予定表、ブックマーク、Wiki、掲示板かな。
公開範囲を自由に指定できれば、文書に属性を与えることで様々な用途に使えるようになるはず。
上では日報と書いているが、範囲を自分のみに絞ればメモのようにもなる。またカテゴリが指定できれば、それによって用途を暗に指すことが出来るようにも出来る。
一般的な、共通のカテゴリを用意し、配置も指定可能であれば、より明確に用途が指定できることになる。
TODOリストや課題リスト、伝言、お知らせなどは、日報の特定カテゴリで公開範囲が指定してあるものともみなせる。(日報と言う表現はおかしいが)
公開範囲が指定できれば、お知らせなどは知らせたい人達だけに知らせられる。
各人のポータルページがあれば、そこに自分が公開範囲に入っているお知らせだけを表示したり、伝言を表示したり出来る。って、こうなるとお知らせも伝言も意味は同じか。下手するとメッセージも同じ意味になるな。

文書の公開範囲とカテゴリが指定できることによって、かなりの機能が実現できそうだ。
ただ、文書によってはフォームを指定したい場合もあるだろうから、その辺りも考えないとな。
公開範囲が自由に指定できると言うのは、思っていた以上にいい機能かも。
そもそも多くの文書の根底にあるものなのかな。
ま、なんかいろいろとごちゃごちゃしてきたので、もう少しよく考えないとな。
でも、基本構造は意外とシンプルにいけそうな予感。

投稿者 Takenori : 18:29 | トラックバック

2006年02月17日

そういえば

Lotus Notesはアクセス可能範囲を指定できたな。
使ったことがあるのではローカルのアドレス帳にグループを入れたものを指定すると最新のが反映されなかったけど。
と言うか、グループウェアではアクセス可能範囲の指定は当たり前?

投稿者 Takenori : 09:47 | トラックバック

mojaviのフィルターチェーン

Mojaviにはフィルターチェーンと言うものがある。
これは、Intercepting Filter パターンを実装したものらしいのだが、どうやって使うのかよくわからない。
Intercepting Filter パターン自体は、アスペクト指向ちっくだ。
要は関数をラップするってことだろう。

Mojaviの使い方は、MVCフレームワークMojaviを使ってみようがわかりやすくていいのだが、フィルタチェーンについてはまだ触れられていない。
ってことで、仕方なくソースコードを追った。
GlobalFilterList.class.php をconfig.phpと同じ場所に置くとグローバルフィルタリストクラスを定義することになる。
モジュール直下に置くとモジュールフィルタリストクラスを定義することになる。
グローバルフィルタリストクラスは、常に適用されるフィルタを登録するクラスで、モジュールフィルタリストクラスは、そのモジュールに適用するフィルタを登録するクラス。
モジュールフィルタリストクラスのファイル名は、ModuleNameFilterList.class.php ( ModuleNameの箇所はモジュール名にする ) となる。
当然、クラス名もファイル名に準じる。
また、フィルタリストクラスは、FilterListを継承する。
実装はコンストラクタのみでよく、その中でフィルタを登録するだけ。
記述例は次のような感じ。

function &GlobalFilterList()
{
  parent::FilterList();
  $this->filters['ExecutionTimeFilter'] = &new ExecutionTimeFilter();
}

ExecutionTimeFilterは初めからあるので、
require_once(FILTER_DIR . 'ExecutionTimeFilter.class.php');
とすれば使える。
で、このフィルタは実行時間を計測してHTMLの最後にコメントとして書き込んでくれる。
フィルタとして実にわかりやすい。
もし、他にもフィルタを追加したければ、$this->filters配列にどんどん追加していけばいい。

このフィルタチェーンは本体に手を加えることなく機能を追加するのに実に便利そうだ。
認証処理やリファラーによるブロック、一時公開停止、ユーザー権限付与などのよく使いそうな機能を手軽に付けたりはずしたり出来る。

投稿者 Takenori : 09:53 | トラックバック

2006年02月18日

PHPにSennaを

グループウェアは PHP で作ろうと思っているのだが、一気にすべてを設計して作ると言うのは大変なので、少しずつ作っていくことにした。
で、プロトタイプを作るのに MySQL でやるのは少し煩わしいと RDBMS には SQLite を使うことにした。
インストールしてある PHP は、Version 4.3.5。
SQLite は入っていなかったので、Win32 版でのインストール方法を調べるとここから php_sqlite.dll を取ってきて、php.ini に extension=php_sqlite.dll の一文を追加すればいいだけ。
これで動く。
ただ、SQLite Library 2.8.14 と表示される。
3系じゃないようだ。
まあ、とりあえずはそれでもいい。
で、全文検索は欲しいので、まずは Senna の PHP 拡張モジュールを作ることにした。

投稿者 Takenori : 09:56 | トラックバック

SennaのPHPのバインディング

ここですでに作られていることを教えてもらった。
と言うことで、SennaのPHP拡張モジュールは作らなくても良さそう。

投稿者 Takenori : 21:40 | トラックバック

SQLite本

ググってたらSQLite入門 すぐに使える軽快・軽量データベース・エンジンという本を発見。
他にもAmazonで検索してみたが、SQLiteのみについて書かれた本はこれぐらいしか見付からなかったので注文した。
なぜかSQLite本と言うのに考えが至らなかったが、出ていてもおかしくないな。
内容はどんなものだろう?
早く届くといいけど。

投稿者 Takenori : 23:00 | トラックバック

2006年02月19日

MeCab (和布蕪) 辞書の構築

Sennaでは MeCab が使われているけど、 MeCab の辞書は約38MBもある。
どうしたものか。
調べてみると、かかしは2MBで茶筅は12MBだった。

そこで、何とかしようととりあえずは MeCab の辞書を再構築することにした。
標準では EUC になっているので、まずはこれを UTF-8 にすることに。

以下は、 mecab-0.90rc9 での話。

初めこのページを参照して辞書の再構築をしていたのだが、どうもうまくいかない。
品詞などが文字化けしていまう。
しばらくして、このページが最新の情報だと気付いた。
が、そうだと気付いても辞書の再構築方法は全然わからず、相変わらず文字化けしてしまっていた。
問題は、dicrc ファイルの

dictionary-charset = utf8

dicrc ファイルのdictionary-charsetは、辞書構築前に変更してはいけない。
変換を行うperlスクリプトを追っていて気付いたのだが、ここで指定されている文字コードがcsvファイルの文字コードだと認識され、この文字コードから指定した文字コードに変換される。
つまり、

dictionary-charset = utf8

と指定すると変換が行われない。
ここは、euc-jpである必要がある。
で、辞書構築終了後、

make dicdir=./ipadic install

でコピーを行い、コピーした先のdicrc ファイルで変更を行う。

後、configure & make を使う場合、

./configure --with-charset=utf8 make

としても、辞書はutf8で作られない。
make途中で

/mecab-dict-index -c utf-8

と言うような箇所があるのだが、上記のようにすると-c utf8となって、これだとeucの辞書が出来てしまう。
makeではなく、

/mecab-dict-index -c utf-8

を直接指定して辞書を作る必要がある。
また、configureは

./configure --with-charset=utf8

ではなく、

./configure --with-charset=utf8 --with-mecab-config=../

としないとmecab-configが見つからないと言われる。
また、Winだと

/mecab-dict-index

は、

perl mecab-dict-index

としないとうまくいかない。

これで何とかUTF-8の辞書が出来た。
すごい時間がかかってしまった。
でも、辞書のサイズは50MBに。
まあ、UTF-8にしたので大きくなるのは当然。

SennaがどのようにMeCab を使っているか見てみると、単に分かち書きをするために使っているようだ。
と言うことは、品詞などのデータは要らない。
これで辞書を小さく出来そうだと思って、mecab-dict-indexを書き換えることを考えながらソースを見ると、-wと言うオプションがあり、これを指定すると分かち書き用の辞書になるようだ。
これで作ると辞書は20MBになった。
後、libmecab.dll が 3.3MB と言うのもでかい。
ソースを見るとucstable.hが妙にでかい。どうも文字コード関連のテーブルのようだ。
ソースを追うとMECAB_USE_UTF8_ONLYと言うデバッグオプション発見。
これを指定してmakeすると276KBになった。
で、辞書とこのDLLをZIPで圧縮すると6.8MBになった。
これぐらいなら配布出来なくはないかな。
まだ大きいことには変わりないけど。
事前にインデックスを作っておき、検索文字列を分割しないような用途であれば辞書を配布しなくていいんだけどなぁ。

投稿者 Takenori : 18:07 | トラックバック

MeCab の設定ファイル

MeCab は実行時に mecabrc ファイルを参照する。
Windows環境下では、 mecabrc ファイルの位置はまずレジストリを参照して見つからなければ、デバッグオプションの MECAB_DEFAULT_RC で指定されたパスを見る。
そして、これはデフォルトだと c:\Program Files\mecab\etc\mecabrc になっている。
これだと任意の位置にMeCab を置きたい場合に困るので、何とかしたい。
そこで、DLLが置かれている位置と同じフォルダにmecabrc ファイルを置き、それを参照してくれるようにすることにした。

そこでまずはDllMainを次のように変更した。

HINSTANCE gDllInst = NULL;
BOOL __stdcall DllMain( HINSTANCE hInst, DWORD dwReason, void* )
{
  if( gDllInst == NULL ) gDllInst = hInst;
  return( TRUE );
}

次に、この変数を参照するために、tagger.cppの std::string getDefaultRc (Param &param) 関数の前に次のようにextern HINSTANCE gDllInstを追加。

#if defined (_WIN32) && ! defined (__CYGWIN__)
extern HINSTANCE gDllInst;
#endif

最後にstd::string getDefaultRc (Param &param) 関数内の return std::string (MECAB_DEFAULT_RC); の前のif define内に

vt = GetModuleFileName( gDllInst, v, size );
if(vt != 0)
{
  char drive[_MAX_DRIVE];
  char dir[_MAX_DIR];
  _splitpath( v, drive, dir, NULL, NULL );
  return std::string(drive) + std::string(dir) + std::string("mecabrc");
}

を追加した。
これで、MeCab がインストールされていなくてレジストリに登録されていない場合、DLLが置かれたディレクトリにあるmecabrc ファイルを参照してくれるようになる。
インストールなしでコピーするだけで使えるようにするには、こうなっていた方が使い勝手がいいだろう。

投稿者 Takenori : 19:12 | トラックバック

2006年02月20日

Sennaのインストールレス化

Senna の設定ファイル ( senna.conf ) などは、コンパイル時のデバッグオプション SENNA_HOME を参照するような作りになっていた。
そして、標準では SENNA_HOME は c:\senna\ になっている。
また、MeCab 異なり、レジストリ参照などは行わず、パスはコンパイル時に決定されたものに固定されるようになっている。
Linux などで install 時に make するような形ならいいけど、 Windows だとこれは使いづらい。

そこで、 MeCab の設定ファイル と同じような方法で DLL が置かれたパスにある senna.conf などを参照するようにした。
これで MeCab と Senna の DLL を好きな場所に置けて、場所を気にせず使える。

後、 Senna をVC.NET 2003 でビルドすると nfkc.c が最適化ありだとコンパイルできない。
関数でかすぎって怒られる。
最適化を切ってやればコンパイルできるが、最適化なしのコードが混じるのは遅くなりそうで使いたくない。
nfkc.c は、 Ruby で自動生成しているようなので、 Ruby スクリプトを変更して作り直そうとしたが、 Ruby スクリプト内でコンパイルしていたり、 ICU 入れたりと大変でやめた。
で、 結局 MinGW で nfkc.c のみをコンパイルして、出来た obj をVCでリンクした。

投稿者 Takenori : 16:37 | トラックバック

Senna の SQLite 組込み方法案

SQLite へ Senna を組込むべく SQLite のソースを追っていたが、初期の案で組み込むのは少し難しそうなので、再考した。

次のような形になると思う。

SELECT * FROM table_name WHERE fulltext_index_match( 'table_name', 'coluon_name', 'words', pid, true ) ORDER BY match_score( pid ) DESC;

table_name が重複するのはかっこ悪いけど諦めてもらおう。
このような形にすると、SQLiteの関数のラッパーとトリガー、ユーザー定義関数のみで実装できそうだ。
SQLite 本体に手を加えなくてもいいので、patch を作ったりしなくても良くてお手軽。
ただし、複数の検索条件を指定したりすることは出来ない。
match_score の引数を増やせば検索条件が識別できるけど、それだと煩雑になる。
複数の検索条件で検索を行うなら、クエリー結果からテンポラリテーブルを作ってそれを使うような形になる。

SELECT pid,match_score(pid) FROM table_name WHERE fulltext_index_match( 'table_name', 'coluon_name', 'words', pid, true );

とすれば、スコアとIDが得られるようになるはず。
そうすれば、それと他のテーブルの内部結合でいろいろ出来るだろう。

後、このような形にしたのは構文拡張が大変そうだったから。
SQLite は、yacc ( or bison ) ではなく、Lemon という独自のパーサージェネレーターを使っているようだ。
これもいじるとなると大変なので、構文拡張ではなく関数のラッパーとトリガー、ユーザー定義関数を使うことにした。
でも、全文検索用の構文があったほうが使いやすいと言えば使いやすいので、将来気力がわいたら拡張するかも。( 過去の傾向からすると、こう言うのはなんだかんだで対応してしまっている気がしないでもない )


関係ないけど、Senna の読みはセナだと今日知った。
センナ だと思ってた。(笑
で、センナってなんだろうなぁ と一人考えてたり。
何となく辞書見たらあった。

センナ【旃那】 (ラテンsenna)生薬の一種。主としてインドおよびエジプト産のマメ科カワラケツメイ属植物数種の葉を乾燥したもの。レイン、アロエエモジンなどを含み下剤に用いる Kokugo Dai Jiten Dictionary. Shinsou-ban (Revised edition) Shogakukan 1988/国語大辞典(新装版)小学館 1988 より

綴り一緒だ。
でも、アイルトン・セナもこの Senna みたい。

投稿者 Takenori : 22:24 | トラックバック

SQLite 本が届いたので読んだ

SQLite入門 すぐに使える軽快・軽量データベース・エンジン が届いたので読んだ。
Amazon のレビューにもあるように、内容の割に値段は高いかな。
SQLite の特徴やバージョン2と3の違いなどが解説された1章(約40ページ)はなかなか良かった。
2章のコマンドラインから SQLite を使うはあんまり読んでいない。SQL 文の解説が主のようだったし。ただ、SQLite 特有の振る舞いなどについて書かれているので、その辺りは良かった。
3章は PHP5 と SQLite でブログシステムを作っている。
一人で使うことが多いブログは SQLite に向いているなと思ったが、 PHP5 が使える環境を持っていないし、セットアップ面倒だし、わざわざブログシステムを作ろうとは思わなかったのでまったく読んでいない。
4章はスクリプト言語からの使い方。
Java、PHP、ASP.NET、ASP、Perl、Ruby、なでしこでの使い方が載っている。
自分の場合、PHP と Perl は使いそうだけど、他は使わなさそう。
しかも、PHP と Perl ならもっと詳しく解説しているページがあると思う。
PHP はオフィシャルのマニュアルの方が詳しい。
5章はコマンドリファレンス。
コマンドラインプログラムの SQLite は使うことが少ないし、SQL 文は 改訂新版 SQLポケットリファレンス があるのでいい。
ただ、 SQLite に特化しているのでその辺りは良いかも。
公式ドキュメントの和訳 (?) SQLite が認識できる SQL でも解説されているが、こちらは固くて少しわかり辛いけど、この本はわかりやすいと感じた。

どうもこの本は対象読者が曖昧な気がする。
初心者向けのような、違うような。
自分としてはこの本からいくつか情報をピックアップしたものの方がいい。
後、C/C++からの使い方がないのも不満。
まあ、使っているのでなくてもいいと言えばいいけど、出来ればAPIリファレンスが欲しかった。
ユーザー定義関数の追加など、公式ページのドキュメントなどではわかり辛いし。
なんか、SQLite の使い方についてまとめたくなってきたけど、面倒臭いな。
DirectShow の使い方もこのブログに点在しているけど、まとめていない。
ブログで書きっぱなしなのを改めないとなぁと常々思ってはいるのだが……
やはり、ブログだとまとめ辛いのが問題かもしれないな。
Wikiを置いてまとめていくのがいいかも。

投稿者 Takenori : 23:01 | トラックバック

2006年03月02日

MeCab の変更が本家へ

MeCab の設定ファイルでDLLと同じディレクトリに設定ファイルを置く変更を書いたが、どうやらこれが本家へ取り込まれるようだ。
これらを組み込んだものが完成したら連絡しようと思っていたけど、その必要はなかったみたい。
どうやって知ったんだろうなぁ? と思いながら MeCab でググったら上述のエントリーが3ページ目に出た。
なぜそんなに上位に……

投稿者 Takenori : 14:51 | トラックバック

SQLite を直接触るのは・・・

SQLite のソースを追うと、SQL文を構文解析>中間コード>最適化>VMで処理といった流れのようだ。
ソースを追いつつ組み込み方を考えていたが、前に書いた方法だとかなり大変そうなことがわかった。
がんばって対応しても良いのだが、そこまで時間をかけるのもどうかと思い、比較的手軽な方法で行こうかと考え中。
具体的には、Senna での検索結果をテンポラリテーブルに格納し、そのテーブル名を返す関数を作るというもの。
利用時は、そのテンポラリテーブルと内部結合してやれば、検索結果と元データを結び付けられるので特に困らないだろう。

投稿者 Takenori : 15:11 | トラックバック

2006年03月19日

ツリーをRDBへ

グループウェアのメモ帳機能をどうするか考えていて、ツリー型の掲示板のような形がいいかもしれないと思った。
各ノードにメモできる必要はなく、フォルダのような扱いにして、その中にメモを入れれるようにしてもいいのだが、別にフォルダにメモ書き出来てもいいよなぁということで、見ため的にはツリー型の掲示板のようにすることにした。

で、これをどのようにしてRDBに保存していくかだけど、すぐに思い付くのは各ノードIDと親ノードIDをペアにして保存していくというもの。
トップノードの親ノードIDは特殊な値にしておけば、それでツリーが構築できる。
ただ、こうするとDBへクエリーを投げまくることになる。
幅優先でツリーを構築していけば、WHEREのところをINで書いたとして、ツリーの深さ回数だけクエリーを投げることになるか。
深くなってくるとSQL文が長くなってくるような気がするけど、実用的な範囲内だろうか?

もしくはルートノードIDをその下につながっているノードすべてが持つようにして、ツリーの子となるノードをすべて取得するという方法もありかな。
ただ、ノードを他のツリーに移せるようにしたいとなった時、そのノードの子すべてのルートノードIDをUPDATEしないといけないのが難点。

素直に各ノードIDと親ノードIDをペアにして保存し、再帰で構築して、保存するときにそのツリーをキャッシュするようにするのが確実かなぁ。

ルートノードIDを持つ持たないはテーブルの構造にかかわるので、ルートノードIDはなしの方向で行くか。
ツリーの構築方法は安全性を考えて幅優先で構築して、キャッシュするようにするかな。

投稿者 Takenori : 22:19 | トラックバック

なぜか日記機能

グループウェアなのになぜか日記機能を追加した。
しかも、日報機能は別に作る予定。

この日記は真(?)の日記。
書けるのは1日に1個だけで、自分以外は見れない。
なんでそんな機能が?って感じだけど、自分が完全にプライベートな日記を書きたいから。
まあ、ユーザー設定でON/OFF出来るようにする予定なので、書かない人は見えないのでどうでもいいという感じ。
で、この日記機能の基本的な機能はほぼ出来た。
書く、見る、編集は実装した。
カレンダー形式の表示や検索、先月の日記を見るなどはまだ出来ていないけど、今の状態でも使える。というか、使ってる。
しかし、ログイン/ログアウト機能の次に日記機能を作ってしまうとは・・・
もう少し作りこんだ後は、メモ帳機能を作ろう。

投稿者 Takenori : 22:41 | トラックバック

2006年05月24日

ユーザー認証のあるWiki

前探して見付からないなぁと思っていたけど、少し前に発見したので使用中。
FreeStyleWiki

ユーザーは「一般」「管理者」のどちらかを設定できる。
作成・編集、参照、添付ファイルの削除の権限を個別に「公開」「一般」「管理者」の中から設定できる。
参照権限はページごとに設定できる。

機能は出来るだけプラグインで実装されていて、基本機能はシンプルなので使いやすい。
ただ、凝ったことをやるのはプラグインでやらないといけないので面倒。
まあ、普段そんなに凝ったことはしないので、その点は問題ない。

少し前からmixi Alert Wikiで使っているのだが、ある程度面識のある人達と少人数で作るのなら、この程度の認証で十分だけど、良く知らない人達にも編集してもらおうとなると、ページごとに編集権を設定できないのが痛い。
ページごとに編集権が設定出来たらかなりいいんだけど。
その辺は凍結で対応するって感じなのかな?

perl で作られていて、認証はすでにあるので、拡張はそんなに大変だとは思わないけど時間が……
少しずつソース見てみるかな。

投稿者 Takenori : 22:50 | トラックバック

2007年01月16日

ローカルで暗号化を

いろいろな文書をオンラインに置きたい。
ローカルに置いていると、どこに置いたか忘れてしまったり、場所が変わると見れなくなって不都合が多い。
その点オンラインにあると、そのような問題が解決する。
グループウェアを作るのなら、そこにいろいろと書きとめておきたい。
しかし、いくらアクセス権を細かく設定できるようにしたとしても、漏洩してしまう問題は避けられない。
パスワード、アクセス権、SSL…… それで十分ともいえるのだが、どうも心もとない。
そこでいろいろと尻込みしていた。

福音はmixiから――
mixiの日記のアクセス権は、友人まで公開、友人の友人まで公開、全体公開と3パターンしかなく、すべての日記で同じアクセス権となる。
アクセス権を設定できないのと大して変わらない。
そんな中異なるアプローチで公開範囲を指定できるようにしようというツールを知った。
日記を暗号化してアップロードし、公開したい人にのみパスワードを教え、読む時に複合化してもらうというものだ。
それを見た時にそれだ!と思った。

つまり、暗号化/複合化はローカルで行い、オンライン上には暗号化されたものを置くというものだ。
ローカルの暗号化器を替えることで、セキュリティー強度を上げたり、独自の暗号化器を使うことも出来る。
当然、見られてもかまわないというか公開したいものは暗号化しなくてもいい。
要は、ローカルでいじってサーバーは置き場所のみ提供すると言うスタイルは使えそうだということ。
これで躊躇していた部分が少し解決した。

投稿者 Takenori : 21:31 | トラックバック

アクセス権

アクセス権はグローバルに定義されたグループ、個別のユーザー、ユーザー定義のグループなどを指定したい。
単一のドキュメントに対してアクセス権の有無をチェックするのは大した処理ではない。
でも、サマリーなどで、新着情報を一覧表示する場合、アクセス権のチェックが重くなりそうな気がする。
そのためあれこれ悩んでいたのだが、手っ取り早く力技実装で行くことに決めた。
重かったら、その時に考えよう。
ってことで、次はひたすら項目挙げて、テーブル分けて、正規化してDBを作ろう。

投稿者 Takenori : 23:31 | トラックバック

2007年01月29日

IPアドレスからおおよその場所の割り出す

hostip.infoを使えば、IPアドレスからおおよその場所がわかる。
ただ、場所はかなり怪しい。
Japanとかはちゃんと出ているけど、それ以上はそんなに制度は良くないみたい。
もし、間違っていたら、登録してやることで登録した場所になる。
とりあえず、自分の環境で割り当てられるIPを何度か登録していたら、自分の場所は精度が上がりそう。

APIも公開されているので、何か面白いことに使えそうな気もする。

投稿者 Takenori : 21:08 | トラックバック

2007年03月04日

検索の分離

RDBMSでデータを管理していると、何でもかんでもRDBで検索したくなる。
しかし、内容を格納したカラムすべてから検索しようとすると、SQL文はどんどん複雑になっていく。
そして、重い。
なんとかうまくやる方法はないものかと思っていたけど、この記事を見てなるほどと思った。

全文検索を組み合わせればいいのか。
RDBからHTMLやXML、単なるテキストにして、それらのインデックスを作れば、すべてから効率的に検索出来るようになる。

投稿者 Takenori : 18:20 | トラックバック

2007年03月11日

掲示板にAtomフィードを

spam書込みを何とかするべく、掲示板拡張中。
いくつか対策は施しているが、まだ1日か2日に1回spam書き込みがある。
より高度なspamフィルタを組み込みたいところだが、まずはAtomフィードに対応し、書き込みを早く知れるようにしたい。
そこで、単に新しい書込みから10件をAtomフィードで吐き出すものを作った。
次は、AtomPP を使って削除が出来る仕組みを作りたい。
新着の中から削除するものを選ぶのなら、今の新着10件のフィードで大丈夫だが、もっと古い書き込みのフィードを取得したい場合など、今のままでは取得できない。

今使っている掲示板はツリー構造を持っているが、Atomフィードではそのような構造をあらわせない。
そこで、独自拡張を考えていたが、そのような用途の拡張はすでにあり、 RFC4685 となっている。
この辺りのことは、Atom 1.0の拡張機能、第2回: 著作権ライセンス、リンクの自動処理、およびスレッドのシンジケートAtomにスレッド情報を埋め込むAtom Threading Extensionsに書かれている。
元々はブログのトラックバックやコメントを表すもののようだが、何に対する返答かと自身への返答のリストがあるので、親と子のリストとみなしてツリー構造を表現できそうだ。

次はクエリか。
AtomPPには、検索関係の機能がなく、Gdataなどの独自拡張がある。
でも、気付いたらAtomPPのドラフトって14まで出てる。
クエリとか増えていたりするんだろうか?
読んでみないと。

投稿者 Takenori : 12:56 | トラックバック

2007年03月13日

掲示板のAtomPP用クエリを考える

やはり、AtomPPにはクエリなどの規定はなさそう。
ただ、next、previous、first、lastのフィードへのリンクを含めることが出来るので、すべてのエントリーを取得するようにすることは出来る。
URLをどうするかと言う問題はあるが。

はてなブックマークフィード仕様GDataを参考にして考えるかな。

問題は、アプリからどうやって取得したいか。
各項目一覧とエントリーの絞込み、ソート方法の指定が出来れば事足りるはず。

各項目一覧は、以下のようなものがリストアップできれば良いだろうか。
・書込み者一覧
・URL一覧

エントリーの絞込みは、以下のものがあれば取り合えず大丈夫。
・最上位書込み ( スレッド )
・スレッド指定
・指定エントリーの返答内
・全文検索
・日付範囲指定
・指定書込み者のエントリー

ソートは、日付、タイトル、書込み者で十分かな。

他に日付の範囲、エントリー数なども欲しくなるかも。

参考:
GData - AtomPP からの拡張

投稿者 Takenori : 18:59 | トラックバック

掲示板spam対策

よく考えれば、掲示板のメール送信を有効にして、POPFileで掲示板spamのバケツを作って、掲示板spamに来たメールから掲示板に飛んで、その書き込みを削除すればいいだけのことなんじゃ……

投稿者 Takenori : 20:36 | トラックバック

2007年07月12日

SQLiteのExtension

前気付かなかったのか新しく追加されたのか、SQLite に Extension を追加する方法があった。
Load An Extension で拡張 DLL を読み込める。
また、3.4.0のソース sqlite-3.4.0/ext/fts1 に全文検索用の Extension がある。
とは言っても、この Extension はたぶん日本語非対応。
でも、これと同じように作ればSennaを使うバージョンも作れそうだ。

投稿者 Takenori : 22:16 | トラックバック

 
Total : Today : Yesterday :