require_once からの卒業〜(尾崎豊風に)

PHP5 では __autoload というメソッドをオーバーライドすることで、require_once から解放されます。Zend Framework を使うことで、この機能を意識せずに使えるようになります。

ディレクトリ構成

Zend Framework には MVC の仕組みがありますが、今回はそれを使わずにオレオレ MVC に適用してみます。

index.php
Test/Container.php
Test/Dao.php
Test/Dao/User.php
Test/Controller/User.php
Test/Logic/User.php
scripts/user/list.php

index.php

リクエストを一手に受けるスクリプトです。Zend_Loader::registerAutoload() を呼ぶことで __autoload を意識せずに使えます。require_once はこの一回ぽっきりです。

<?php
set_include_path(
    get_include_path() .
    PATH_SEPARATOR . '/usr/local/ZendFramework-1.5.1/library'
);

// using autoload
require_once 'Zend/Loader.php';
Zend_Loader::registerAutoload();

// test controller
$ctl = Test_Container::getController('User');
$ctl->listAction();
?>

Test/Container.php

DI コンテナ風のクラスです。設定を外だしすれば、S2Container 風になると思います。

<?php
class Test_Container
{
    public static function getController($name)
    {
        $name  = 'Test_Controller_' . $name;
        $controller = new $name();
        return $controller;
    }

    public static function getDao($name)
    {
        $db   = Test_Dao::getHandle();
        $name = 'Test_Dao_' . $name;
        $dao  = new $name(array('db' => $db));
        return $dao;
    }

    public static function getLogic($name)
    {
        $name  = 'Test_Logic_' . $name;
        $logic = new $name();
        return $logic;
    }
}

Test/Dao.php

Dao (Data Access Object) の親クラスです。

<?php
class Test_Dao {
    public static function getHandle()
    {
        $db = new Zend_Db_Adapter_Pdo_Pgsql(
            array(
                'host'     => 'localhost',
                'username' => 'fugafuga',
                'password' => 'hogehoge',
                'dbname'   => 'foo_bar'
            )
        );
        return $db;
    }
}

Test/Dao/User.php

具体的な Dao です。RubyActiveRecord 風の記述で非常に簡単に O/R マッパーを使うことができます。

<?php
class Test_Dao_User extends Zend_Db_Table_Abstract
{
    protected $_name = 'user_data'; // テーブル名
    protected $_primary = 'id'; // 主キー名
}

Test/Controller/User.php

具体的なコントローラです。最後にビューを呼んでいます。

<?php
class Test_Controller_User {
    public function listAction() {
        // ロジックを呼ぶ
        $logic = Test_Container::getLogic('User');
        $users = $logic->getList();

        // ビューを呼ぶ
        $view = new Zend_View(array('basePath' => '.'));
        $view->assign('title', 'User List');
        $view->assign('users', $users);
        print $view->render('user/list.php');
    }
}

Test/Logic/User.php

具体的なビジネスロジックを記述します。

<?php
class Test_Logic_User
{
    public function getList()
    {
        $user_dao = Test_Container::getDao('User');
        $users = $user_dao->fetchAll(
            $user_dao->select()->where('disable = ?', 0)
        );
        return $users;
    }
}

scripts/user/list.php

テンプレートファイルです。

<html>
    <head>
     <title><?= $this->title ?></title>
    </head>
    <body>
     <ul>
<?php foreach ($this->users as $user) : ?>
      <li><?= $user->id ?> <?= $user->name ?></li>
<?php endforeach; ?>
     </ul>
    </body>
</html>