紹介 その2 クラスロードについて

※この記事は以下の公式ドキュメントを元に書いています。
http://kohanaframework.org/3.2/guide/kohana/conventions

クラスロード(autoload)について

Kohanaのクラスロードの仕組みはPHP5から登場したautoloadの仕組みを利用しています。コードを書くことになるapplicationの下を見てみましょう。


application/

bootstrap.php
cache/
classes/
controller/
model
config/
i18n/
logs/
messages/
views/


MVCフレームワークに触れている人であれば特に違和感を感じないと思います。ここであなたがPHPのクラスファイルを作成していくのはclasses/以下になります。controllerとmodelというディレクトリが作られていますが、それらについては次回に紹介します。
ここでsystemの下も覗いてみましょう。ほぼapplication下と同じ構成になっていて、classesの下には沢山のクラスファイルが置かれているはずです。

system/

classes/
arr.php
cli.php
controller.php
........
config/
guide/
i18n/
media/
messages/
tests/
utf8/
views/


ではsystem/classes/arr.phpを開いてみます。

<?php defined('SYSPATH') or die('No direct script access.');

class Arr extends Kohana_Arr {}

クラス名はArr。実態は無く、Kohana_Arrを継承しているだけです。これは意味のあることで、なぜこうしているかは後で解説します。
application、system、modules問わず、PHPクラスはclassesの下に作ります。そしてautoloadを利用する都合上、ファイル名やクラス名にはルールがあり、それに従う必要があります。

  1. サブディレクトリの下に配置する場合、ディレクトリとクラス名は_(アンダーバー)で区切る
  2. ファイル名、ディレクトリ名は全て小文字にする
  3. クラスは全てclassesの下に配置する

公式ドキュメントの例が分かりやすいので紹介します。

Class Name File Path
Controller_Template classes/controller/template.php
Model_User classes/model/user.php
Database classes/database.php
Database_Query classes/database/query.php
Form classes/form.php

先ほどのsystem/classes/arr.phpはファイル名がarr.phpなのでクラス名はArrになっています。継承しているKohana_Arrはsystem/classes/kohana/arr.phpPHPファイルがあります。このようにルールに従っていればrequireやincludeする必要はありません。

これはapplication/classesの下も同じです。application/classes/controller/welcome.phpがデフォルトコントローラとして作成されていますが、それのクラス名はController_Welcomeになっています。もしapplication/classes/arr.phpを作成したらどうなるかと言うと、その環境下ではどこのクラスから参照したArrであっても、systemではなくapplicationの物が参照されることになります。Kohanaのautoloadには優先順位があり、application > modules > systemとなっています。applicationに置いたクラスが最も優先度が高く、他のmodulesやsystemにArrクラスがあったとしてもapplicationの物がロードされます。

ここで、なぜsystemのArrに実態が無く、Kohana_Arrを継承しているだけなのかの解説をします。もしArrの機能に不満があり、ちょっと拡張したくなったとします。例えば1つのメソッドを増やしたいのであれば、Arrを継承してMyArrを作成すれば良いと思いますが、既にArrを多くの場所で利用してしまっている場合クラス名を変えるのは難しいです。
そこで、applicationのclassesにArrクラスを作成し、Kohana_Arrを継承するようにします。そうすればautoloadはsystemのArrをロードせずにapplicationのArrをロードするようになります。そしてメソッドが定義されているKohana_Arrはsystemの物がロードされるので、applicationのArrから呼び出せるしメソッドをオーバーライドする事も可能です。
このような拡張を容易にするために、systemに容易されているクラスのほとんどはこのような形になっています。

クラスはrequireやincludeでロードするよりも、必要な時点で読み込むautoloadを利用した方が一般的に高速に動作します。色々なクラスを読み込むWebフレームワークであればそれなりの差になると思います。Kohanaのルールに従ったクラスを用意するようにしましょう。

紹介 その3 モジュールについて - isherの日記