已经使用了许多你想象的ORM。目前我正在用RedBean PHP进行爱恨交织。在这里,我们开始......经过几个小时的研究后,我对这是解决这个非常基本的问题的最佳方法产生了疑问(在这种情况下,最佳方式意味着更好地适应RedBean的易用性理念):
限制对类的某些属性的访问是很常见的,因此我们可以防止某些类型的错误数据操作。这通常是通过充分利用吸气剂和固定剂来实现的。但是就已经了解的RedBean而言,本机类中没有正式的setter,只有一些可以在数据库中更改和保存的公共属性。
我想要做的是保护某些属性不被手动更改,因此我可以避免其他程序员产生任何类似的奇怪:
$beam->insertion_date = 'yesterday';
R::store($beam);
显然,在插入行之后永远不应该更改该字段,但我们不能相信没有人会这样做。有没有办法实现像insert_date一样受保护的属性或者以某种方式使它无法访问?
我有一种感觉,最好的方法是使用$beam->setMetadata()
并声明不应该更改给定的属性,但我不知道如何在RedBean中实现这一点但仍然无法实现在官方手册中找到足够的信息。任何帮助表示赞赏。
感谢阅读。
答案 0 :(得分:3)
保护数据库免受未经授权或意外修改的唯一防弹方法是使用数据库的权限系统(GRANT
和REVOKE
),方法是使用具有特定权限的不同用户配置文件。等级等。
可能不容易实现,但通过保留(自定义)代码中的权限,总会存在漏洞。
答案 1 :(得分:1)
另一种方法是将列的数据类型设置为具有指定状态的类型。
例如,如果将varchar(255)更改为varchar(254),RedBeanPHP将发现更改并保留列,因为它现在是指定的列,对于int,您可以使用INT(10)。特殊类型永远不会被转换:ENUM / DATE等。
答案 2 :(得分:0)
找到解决方案!
在将数据放回数据库之前,请测试是否以编程方式更改了不应更改的值。
这就是示例模型现在的样子:
class Model_book extends RedBean_SimpleModel{
protected $before = false;
public function open(){
if($this->bean->id){
$this->before = clone($this->bean);
}
}
public function update(){
if($this->bean->id){
if($this->before->insertion_date != $this->bean->insertion_date){
throw new exception ("The insertion_date can't be changed.");
}
}
}
}
现在,以下代码将导致异常:
$beam->insertion_date = 'yesterday';
R::store($beam);
注意:使用RedBean的元信息API会更好 解决方案,但添加(仅)此验证是没有意义的 标准没有在RedBean之上添加完整的验证层。上 另一方面,添加自定义完整验证将变得无用 在不久的将来,内置验证会被添加到ORM中(I 打赌它会发生),所以我现在就把它留下来。
希望有所帮助。