当前位置: 首页 > 文档资料 > FuelPHP 中文文档 >

時序模型 - Orm 套件

优质
小牛编辑
125浏览
2023-12-01

简介

时序模型比它听起来的更不可怕。

通常一个资料库实体代表资料表中的一列,当它被更新时,旧资讯会被覆写。时序模型允许资料以时间被引用,它使得在一个所给时间查询一个实体状态变为可能。

例如,假设你希望追蹤产品的变更,如此当一个订单交易成功你可以知道产品的状态而无须重複订单资料表中的资料。你可以让产品有时序并且使用订单时间来引用当时下订产品的状态,而非它们目前的状态,不使用时序资料的情况下就可能会是当下的状态。

时序模型也可被用在审核变更的事物像 wiki 页面。任何变更会被自动记录,而不须使用一张独立的 log 资料表。

「实体」可能是你设计中的任何项目,例如产品、使用者、多媒体文件夹、任何你会使用做为模型的可被认为是一个实体。时序模型能让你透过储存变更,来追蹤这些实体随着时间推移的变化,每一组新的变更被称为一个「修订版本」。因为每一个修订版本与时间(时序)资料一起储存,这使得取得一个实体在所给任何时间的状态变为可能。

这个时序模型的实现在相同资料表储存实体的修订版本做为原始资料,不再需要重複的 "log" 资料表。虽然这里的实现不是实现修订版本的唯一方式,它是在 ORM 所给的限制之下最弹性的方式,而且事实上,它必须在多种资料库环境下运作。

为什幺在 ORM 中实现而不是选择一个允许该功能的资料库系统?

在 ORM 中实现时序功能能让技术被抽象出资料库层,这能让 ORM 支援的任何资料库使用时序模型,提供更大的灵活性。此模型不会取代使用支援时序资讯的资料库使用能力,但提供一个「开箱即用」的实现。

使用

资料表必须被设置一个实体 ID 的複合主键,一个标准的自动递增数字(例如),以及代表有效时间跨度的时间戳记。

class Model_MyTemporal extends Orm\Model_Temporal
{
	protected static $_primary_key = array('id', 'temporal_start', 'temporal_end');
	protected static $_temporal = array(
		'start_column' => 'temporal_start', // 包含此笔资料有效起始时间的行名称
		'end_column' => 'temporal_end', // 包含此笔资料有效结束时间的行名称
		'mysql_timestamp' => false, // 如果设为 true 将使用 MySQL 时间戳记,否则是 UNIX 时间戳记
	);
}

请注意,主键应该是一个实体 ID 以及时序时间戳记的複合键。

任何使用时序模型定义的关联应该只涉及 ID,而不是 ID 和时间戳记。

find()

find 方法与正规模型的实现运作相同,除了只在实体最新版本,WHERE 子句被添加到 SELECT。

find_revision($id, $timestamp=null, $relations = array())

此方法可以被用来查询实体在所给时间的状态。

静态
参数
参数预设描述
$id必要要搜寻实体的 ID。
$timestamp
null
要引用实体所在的时间。null 将回传最新的修订版本。
$relations
array
要与该实体一起载入的关联的名称。
回传单一的 Model_Temporal 子类别
範例
Model_Product::find_revision($id, '2012-11-09 12:04:00', array('images', 'reviews'));

任何透过 find_revisionfind_revisions 取回的模型应该被认为是唯读,因为它不应该有可能修改过去!

find_revisions_between($id, $earliestTime = null, $latestTime = null)

此方法将回传实体在所给时间之间的状态。

静态
参数
参数预设描述
$id必要要搜寻实体的 ID。
$earliestTime
null
要寻找最早的修订版本时间,或 null 无限多先前的修订版本。
$latestTime
null
字串
整数
要寻找最新的修订版本时间,或null 无限多的修订版本(直到最新)。
回传Model_Temporal 子类别的阵列
範例
Model_Product::find_revisions_between($id, '2012-11-09 12:04:00', '2012-12-10 19:00:00');

目前还不能在使用 find_revisions_between 的同时选择关联。

delete($cascade = null, $use_transaction = false)

此方法将从资料库删除物件。它与一般模型的删除功能运作的方式完全相同,除了资讯不会从资料库被移除。这意味着你仍然可以引用该物件在所给时间,但它就目前而言不再有效。

静态
範例
Model_Product::find(5)->delete();

串联删除将正常删除。任何不是 Soft 或 Temporal 的模型也会正常删除。

overwrite($cascade = null, $use_transaction = false)

能让资讯被储存而不用建立一个新的修订版本。与 Model::save() 的运作相同。

静态
範例
$product = Model_Product::find(5);
$product->name = 'Super Awesome 12000';
// Product 会更新而不会在资料库中建立新的一笔资料。
$product->overwrite();

restore()

如果一个实体已经被删除,此方法还原该实体到目前状态。如果该实体没有被删除将不会发生什幺事。

静态
範例
Model_Product::find_revision(5, '2012-11-09 12:04:00')->restore();

purge()

从资料库移除此实体的所有修订版本。这是永久的!它不能被撤消。

静态
範例
Model_Product::find(5)->purge();

这不能被撤消,它将从资料库删除实体的所有修订版本。如果你这样做资料将被摧毁!