找回密码
 立即注册

QQ登录

只需一步,快速开始

查看: 2466|回复: 0

[教程] 数据源架构模式之活动记录

[复制链接]
发表于 2013-4-14 09:58:35 | 显示全部楼层 |阅读模式 来自 中国–广东–湛江
【活动记录的意图】
  一个对象,它包装数据表或视图中某一行,封装数据库访问,并在这些数据上增加了领域逻辑。
  【活动记录的适用场景】
  适用于不太复杂的领域逻辑,如CRUD操作等。
  【活动记录的运行机制】
  对象既有数据又有行为。其使用最直接的方法,将数据访问逻辑置于领域对象中。
  活动记录的本质是一个领域模型,这个领域模型中的类和基数据库中的记录结构应该完全匹配,类的每个域对应表的每一列。
  一般来说,活动记录包括如下一些方法:
  1、由数据行构造一个活动记录实例;
  2、为将来对表的插入构造一个新的实例;
  3、用静态查找方法来包装常用的SQL查询和返回活动记录;
  4、更新数据库并将活动记录中的数据插入数据库;
  5、获取或设置域;
  6、实现部分业务逻辑。
  【活动记录的优点和缺点】
  优点:
  1、简单,容易创建并且容易理解。
  2、在使用事务脚本时,减少代码复制。
  3、可以在改变数据库结构时不改变领域逻辑。
  4、基于单个活动记录的派生和测试验证会很有效。
  缺点:
  1、没有隐藏关系数据库的存在。
  2、仅当活动记录对象和数据库中表直接对应时,活动记录才会有效。
  3、要求对象的设计和数据库的设计紧耦合,这使得项目中的进一步重构很困难
  【活动记录与其它模式】
  数据源架构模式之行数据入口:活动记录与行数据入口十分类似。二者的主要差别是行数据入口 仅有数据库访问而活动记录既有数据源逻辑又有领域逻辑。
  【活动记录的PHP示例】
  1. <?php     /**   * 企业应用架构 数据源架构模式之活动记录 2010-10-17 sz   * @author phppan.p#gmail.com  http://www.phppan.com   * 哥学社成员(http://www.blog-brother.com/)   * @package architecture   */    /**   * 定单类   */ class Order {         /**       *  定单ID       * @var <type>       */     private $_order_id;         /**       * 客户ID       * @var <type>       */     private $_customer_id;         /**       * 定单金额       * @var <type>       */     private $_amount;         public function __construct($order_id, $customer_id, $amount) {          $this->_order_id = $order_id;          $this->_customer_id = $customer_id;          $this->_amount = $amount;      }         /**       * 实例的删除操作       */     public function delete() {          $sql = 'DELETE FROM Order SET WHERE order_id = ' . $this->_order_id . ' AND customer_id = '  . $this->_customer_id;          return DB::query($sql);      }         /**       * 实例的更新操作       */     public function update() {      }         /**       * 插入操作       */     public function insert() {      }         public static function load($rs) {          return new Order($rs['order_id'] ? $rs['order_id'] : NULL, $rs['customer_id'], $rs['amount'] ? $rs['amount'] : 0);      }     }     class Customer {         private $_name;      private $_customer_id;         public function __construct($customer_id, $name) {          $this->_customer_id = $customer_id;          $this->_name = $name;      }         /**       * 用户删除定单操作 此实例方法包含了业务逻辑       * 通过调用定单实例实现       * 假设此处是对应的删除操作(实际中可能是一种以某字段来标记的假删除操作)       */     public function deleteOrder($order_id) {          $order = Order::load(array('order_id' => $order_id, 'customer_id' => $this->_customer_id));          return $order->delete();      }         /**       * 实例的更新操作       */     public function update() {      }         /**       * 入口类自身拥有插入操作       */     public function insert() {      }         public static function load($rs) {          /* 此处可加上缓存 */         return new Customer($rs['customer_id'] ? $rs['customer_id'] : NULL, $rs['name']);      }         /**       * 根据客户ID 查找       * @param integer $id   客户ID       * @return  Customer 客户对象       */     public static function find($id) {          return CustomerFinder::find($id);      }     }     /**   * 人员查找类   */ class CustomerFinder {         public static function find($id) {          $sql = 'SELECT * FROM person WHERE customer_id = ' . $id;          $rs = DB::query($sql);             return Customer::load($rs);      }  }     class DB {         /**       * 这只是一个执行SQL的演示方法       * @param string $sql   需要执行的SQL       */     public static function query($sql) {          echo '执行SQL: ', $sql, '
  2. ';              if (strpos($sql, 'SELECT') !== FALSE) { //  示例,对于select查询返回查询结果              return array('customer_id' => 1, 'name' => 'Martin');          }      }     }     /**   * 客户端调用   */ class Client {         /**       * Main program.       */     public static function main() {                header('Content-type:text/html; charset=utf-8');             /* 加载客户ID为1的客户信息 */         $customer = Customer::find(1);             /* 假设用户拥有的定单id为 9527*/         $customer->deleteOrder(9527);      }     }     Client::main();  ?>
复制代码
同前面的文章一样,这仅仅是一个活动记录的示例,关于活动记录模式的应用,可以查看Yii框架中的DB类,在其源码中有一个CActiveRecord抽象类,从这里可以看到活动记录模式的应用
  另外,如果从事务脚本中创建活动记录,一般是首先将表包装为入口,接着开始行为迁移,使表深化成为活动记录。
  对于活动记录中的域的访问和设置可以如yii框架一样,使用魔术方法__set方法和__get方法。


发帖求助前要善用【论坛搜索】功能,那里可能会有你要找的答案;

如何回报帮助你解决问题的坛友,好办法就是点击帖子下方的评分按钮给对方加【金币】不会扣除自己的积分,做一个热心并受欢迎的人!

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则 需要先绑定手机号

关闭

站长推荐上一条 /1 下一条

QQ|侵权投诉|广告报价|手机版|小黑屋|西部数码代理|飘仙建站论坛 ( 豫ICP备2022021143号-1 )

GMT+8, 2024-11-23 05:18 , Processed in 0.036622 second(s), 7 queries , Redis On.

Powered by Discuz! X3.5

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表