Синглтон в сочетании с фабричным шаблоном в PHP5 - PullRequest
4 голосов
/ 30 ноября 2009

Каков наилучший метод для использования шаблона одноэлементного проектирования в сочетании с шаблоном фабричного метода в PHP5? Мой самый простой сценарий использования этого - выборочное соединение с базой данных только один раз для каждого типа базы данных.

1 Ответ

10 голосов
/ 30 ноября 2009

одноэлементная фабрика для подключения к БД:

class Registry
{
    private static $_objects;

    public static function set($key, $object)
    {
        if (!array_key_exists($key, self::$_objects)) self::$_objects[$key] = $object;
    }

    public static function get($key)
    {
        if (array_key_exists($key, self::$_objects)) return self::$_objects[$key];
        else return false;
    }
}

class DBFactory
{
    public static function getConnection($type)
    {
        switch ($type) {
            case 'pdo':
                if (!(Registry::get('DB_PDO') instaceof DbPdo)) Registry::set('DB_PDO', new DbPdo('user', 'pass', ...));
                return Registry::get('DB_PDO')
            case 'mssql':
                //same for other connections
            //...
        }
    }
}

использование:

$factory = DBFactory::getConnection('pdo');

Синглтоны больше не нужны, потому что все методы можно вызывать статически ... Но классы базы данных все еще могут рассматриваться как одиночные, потому что в вашем приложении будет только один их экземпляр.

Таким образом, тот же эффект создается при использовании шаблонов фабрики и реестра.

Реестр можно заменить, сделав ваши классы базы данных синглетонами, тогда фабрика будет выглядеть так:

class DBFactory
{
    public static function getConnection($type)
    {
        switch ($type) {
            case 'pdo':
                return DbPdo::getInstance('user', 'pass', ...);
            case 'mssql':
                //same for other connections
            //...
        }
    }
}

class DbPdo
{
    private static $_instance;

    private function __construct($user, $pass, ...){ //instantiate object }

    public static function getInstance($user = null, $pass = null, ...)
    {
        if (!(self::$_instance instanceof DbPdo)) self::$_instance = new DbPdo($user, $pass, ...);
        return self::$_instance;
    }
}

Таким образом, у вас есть выбор сделать все объекты БД одиночными или использовать реестр. Лично я бы пошел с реестром, потому что он может быть использован для хранения любых типов объектов, даже тех, где вы не хотите делать класс одиночным.

Выбор дизайна всегда зависит от личного вкуса ...

...