php共享数据库连接(设计模式帮助)

时间:2011-02-21 21:47:08

标签: php design-patterns database-abstraction

我有一个小的php应用程序,我想在一些“模型”类型类之上构建一个db抽象层。

我正在使用ezSQL_mysql来完成数据库工作。

我的问题是设计应用程序的最佳方式是什么?我应该使用单例模式来共享数据库连接吗?我的“模型”类应该扩展ezSQL_mysql吗?或者也许我完全不在这里,需要做点别的事情。

我需要的是这样的东西

Controller.php

   $db = new ezSQL_mysql($db_user, $db_passwd, $db_database, $db_host);


   $user = new User();
   $user->update_email($new_email);

   $sale = new Sale();
   $sale->purchase($amount); 

User_model.php

class User {

   /* uses $db connection */
   function update_email(){
     /* do something */
   };
}

Sale_model.php

class Sale {   
   /* uses $db connection*/

   function purchase () {
    /* do something */ 
   }
}

3 个答案:

答案 0 :(得分:3)

数据库连接单例可能有问题。幸运的是,没有必要进行连接共享。您可以拥有一个连接管理器类,当给定以前使用的主机,用户和数据库名称时,它返回已经打开的连接。

abstract class ConnectionManager {
    protected $connections = array();
    function connect($host, $db, $user, $pw) {
        if (! isset($this->connections[$host][$db][$user])) {
            $this->connections[$host][$db][$user] = $this->newConnection($host, $db, $user, $pw));
        }
    }
    abstract protected function newConnection($host, $db, $user, $pw);
}

class EzSQLConnectionManager extends ConnectionManager {
    protected function newConnection($host, $db, $user, $pw) {
        return new ezSQL_mysql($user, $passwd, $database, $host);
    }
}

此处未解决的是如何安全地存储用户凭据。密码不应该在整个脚本中无所不在地传播,这种方法可能会导致你这样做。

答案 1 :(得分:2)

对于小型应用程序,绝对使用域对象模式。也就是说,每个对象代表db实体。

然后你可以决定天气你将使用mapper模式向db添加一些更复杂的查找。

如果您更喜欢经过测试的解决方案,可以查看Zend_Db。它涵盖了您需要的一切,从数据库适配器,工厂等。它基本上实现了网关模式,但实现类似mapper的东西已经在参考手册中显示。

其他解决方案包括ORM,如Doctrine或Propel。

不应过度使用模式。如果它是一个小应用程序,尽可能简单地解决问题。如果您正在做这个实验,请尝试使用Doctrine。那些图书馆有时候会非常棒。

答案 2 :(得分:0)

好的......所以小应用程序的需求增长,按照惯例我决定使用MVC框架,而不是滚动我自己的松散类来管理持久连接和抽象数据库层。

所以现在我正在使用CodeIgniter http://www.codeigniter.com/,它基本上以更易于管理的方式完成了我想要做的事情。

感谢其他答案。