博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
数据源架构模式之活动记录
阅读量:5825 次
发布时间:2019-06-18

本文共 2869 字,大约阅读时间需要 9 分钟。

一、概念

活动记录(Active Record):一个对象,它包装数据库表或视图中某一行,封装数据库訪问。并在这些数据上添加了领域逻辑。

对象既有数据又有行为。

活动记录使用直截了当的方法。把数据訪问逻辑置于领域对象中。

 

二、实现简单活动记录

活动记录在php很多框架中都有应用。如cakephp。

Php代码  收藏代码
  1. <?php  
  2. /** 
  3.  * 行数据入口类 
  4.  */  
  5. class OrderGateway {  
  6.     /*定义元数据映射*/  
  7.     private $_name;  
  8.     private $_id;  
  9.    
  10.     public function __construct($id$name) {  
  11.         $this->setId($id);  
  12.         $this->setName($name);  
  13.     }  
  14.    
  15.     public function getName() {  
  16.         return $this->_name;  
  17.     }  
  18.    
  19.     public function setName($name) {  
  20.         $this->_name = $name;  
  21.     }  
  22.    
  23.     public function getId() {  
  24.         return $this->_id;  
  25.     }  
  26.    
  27.     public function setId($id) {  
  28.         $this->_id = $id;  
  29.     }  
  30.    
  31.     /** 
  32.      * 入口类自身拥有更新操作 
  33.      */  
  34.     public function update() {  
  35.         $data = array('id' => $this->_id, 'name' => $this->_name);  
  36.    
  37.         $sql = "UPDATE order SET ";  
  38.         foreach ($data as $field => $value) {  
  39.             $sql .= "`" . $field . "` = '" . $value . "',";  
  40.         }  
  41.         $sql = substr($sql, 0, -1);  
  42.         $sql .= " WHERE id = " . $this->_id;  
  43.         return DB::query($sql);  
  44.     }  
  45.    
  46.     /** 
  47.      * 入口类自身拥有插入操作 
  48.      */  
  49.     public function insert() {  
  50.         $data = array('name' => $this->_name);  
  51.    
  52.         $sql = "INSERT INTO order ";  
  53.         $sql .= "(`" . implode("`,`"array_keys($data)) . "`)";  
  54.         $sql .= " VALUES('" . implode("','"array_values($data)) . "')";  
  55.    
  56.         return DB::query($sql);  
  57.     }  
  58.    
  59.     public static function load($rs) {  
  60.         /* 此处可加上缓存 */  
  61.         return new OrderGateway($rs['id'] ? $rs['id'] : NULL, $rs['name']);  
  62.     }  
  63.    
  64. }  
  65.   
  66. /** 
  67.  * 上面内容与行数据入口一样 
  68.  * 此类为领域逻辑,这里新建个类,不採用static 
  69.  */  
  70. class OrderAccess {  
  71.     public function find($id) {  
  72.         $sql = "SELECT * FROM order WHERE id = " . $id;  
  73.         $rs = DB::query($sql);  
  74.    
  75.         return OrderGateway::load($rs);//这里返回的行对象  
  76.     }  
  77.   
  78.     public function insert($data){  
  79.         OrderGateway::load($data)->insert();  
  80.     }  
  81.   
  82.     public function updateName($id,$name){  
  83.         $rs = array('id' => $id,'name' => $name);  
  84.         OrderGateway::load($rs)->update();  
  85.     }   
  86.   
  87.     public function findAll() {  
  88.         $sql = "SELECT * FROM order";  
  89.         $rs = DB::query($sql);  
  90.    
  91.         $result = array();  
  92.         if (is_array($rs)) {  
  93.             foreach ($rs as $row) {  
  94.                 $result[] = OrderGateway::load($row);  
  95.             }  
  96.         }  
  97.    
  98.         return $result;  
  99.     }  
  100.    
  101. }  
  102.    
  103. class DB {  
  104.    
  105.     /** 
  106.      * 这仅仅是一个运行SQL的演示方法 
  107.      * @param string $sql   须要运行的SQL 
  108.      */  
  109.     public static function query($sql) {  
  110.         echo "运行SQL: "$sql" <br />";  
  111.     }  
  112. }  
  113.    
  114. /** 
  115.  * client调用 
  116.  */  
  117. class Client {  
  118.     public static function main() {  
  119.         header("Content-type:text/html; charset=utf-8");  
  120.    
  121.         $access = new OrderAccess();  
  122.         $order = $access->find(1);  
  123.         echo $order->getName();  
  124.   
  125.         $access->insert(array('name' => 'xxxxx'));  
  126.         $access->update(1,'xxxxx');  
  127.     }  
  128. }  
  129.    
  130. Client::main();  
  131. ?

    >  

 

三、执行机制

●活动记录的本质是一个领域模型,每条活动记录负责向数据库保存数据。从数据库载入数据以及处理作用于数据之上的领域逻辑。

 

●此模式没有隐藏关系数据库的存在这个事实,因此通常使用此模式的同一时候差点儿不用其它对象关系映射模式。

 

●活动记录和行数据入口十分相似,之前也多次提及。行数据入口仅有数据库訪问而活动记录既有数据源逻辑又有领域逻辑。

 

●因为活动记录和数据库间的紧耦合,在这个模式中经常使用静态查找方法(样例採用的是新建类。这样更便于測试)。

 

●活动记录通常具有例如以下方法:

1、由SQL结果集中的一行构造一个活动记录实例(例中的OrderAccess->find方法

2、为将来对表的插入构造一个新的实例

3、用静态查找方法来包装经常使用的SQL查询和返回活动记录(样例採用新建类)

4、更新数据库并将活动记录中的数据插入数据库(例中的OrderAccess->update方法

5、获取和设置域(例中的OrderGateway getName setName方法)

6、实现部分业务逻辑

 

四、使用场景 

1、领域模型

活动记录适用于不太复杂的领域逻辑,如CRRD等。

仅当活动记录对象和数据库中表直接相应,才比較有效。假设业务逻辑复杂,就会想到使用对象的直接关系、集合和继承等。

它们都难以映射到活动记录。

 

2、事务脚本

活动记录能够降低事务脚本代码反复的痛苦。

 

3、表模块(不考虑)

转载地址:http://rmidx.baihongyu.com/

你可能感兴趣的文章
.NET 设计规范--.NET约定、惯用法与模式-2.框架设计基础
查看>>
win7 64位+Oracle 11g 64位下使用 PL/SQL Developer 的解决办法
查看>>
BZOJ1997:[HNOI2010]PLANAR——题解
查看>>
BZOJ1014:[JSOI2008]火星人prefix——题解
查看>>
使用Unity3D引擎开发赛车游戏
查看>>
HTML5新手入门指南
查看>>
opennebula 开发记录
查看>>
ubuntu 修改hostname
查看>>
sql 内联,左联,右联,全联
查看>>
C++关于字符串的处理
查看>>
6、Web Service-拦截器
查看>>
Flask 源码流程,上下文管理
查看>>
stream classdesc serialVersionUID = -7218828885279815404, local class serialVersionUID = 1.
查看>>
ZAB与Paxos算法的联系与区别
查看>>
java 读取本地的json文件
查看>>
Breaking parallel loops in .NET C# using the Stop method z
查看>>
修改故障转移群集心跳时间
查看>>
[轉]redis;mongodb;memcache三者的性能比較
查看>>
微软职位内部推荐-Sr DEV
查看>>
让你的WPF程序在Win7下呈现Win8风格主题
查看>>