Yii2 保存前
Yii2 beforeSave
我有一个 Controller 和一个用 giiant 生成的 updateAction:
public function actionUpdate($id) {
$model = $this->findModel($id);
if ($model->load($_POST) && $model->save()) {
return $this->redirect(['view', 'id' => $model->id]);
} else {
return $this->render('update', [
'model' => $model,
]);
}
}
我想通过覆盖模型中的 beforeSave 来重命名文件:
public function beforeSave($insert) {
if ($this->isAttributeChanged('name')) {
rename($this->getOldAttribute('name') . '.pdf', $this->name . '.pdf');
}
parent::beforeSave($insert);
}
好像是保存了模型,保存后还是渲染出来的表格,怎么可能呢。我确定这是因为 beforeSave
,因为如果我将其注释掉,一切正常。 beforeSave 的使用怎么会导致这种不合逻辑的行为呢?我错过了什么?非常感谢!
Yii 和其他 MVC 框架具有这些功能。
虽然您可以在控制器中编写 "before save" 代码,但在 save() 函数之前 - 更推荐使用 beforeSave() 函数。
原因一:MVC中的M
beforeSave 与模型相关,因此在模型文件中使用处理模型属性(字段)的代码比在控制器中使用该代码更合乎逻辑。
原因 2:保存是为了插入和更新
您在插入新记录和更新现有记录时使用 save()。如果不使用 beforeSave 内置函数,您必须在保存代码之前有 2 个 "manual" 实例。 ("Waste" 代码行)
原因 3:从另一个控制器保存模型
如果你被要求扩展你的应用程序,现在你不得不面对一个需要保存相同模型的新控制器(出于某种原因 - 只是一种可能的情况) - 你将不得不将您的 "before save" 代码复制到该控制器。如果您使用的是内置的 beforeSave 函数,则不需要。
总而言之,框架的主要目的是减少您需要编写的代码,同时保持任何逻辑(MVC 分离)。虽然您可以做不同的事情,但为什么不使用已经存在的东西呢?
一个简单的例子:
我有一个带有两个日期字段的 table。每次我尝试执行插入或更新时,我都需要获取当前系统日期并根据操作类型进行操作。
public function beforeSave() {
if ($this->isNewRecord) {
$this->insertDate = new CDbExpression('NOW()');
} else {
$this->updateDate = new CDbExpression('NOW()');
}
return parent::beforeSave();
}
我写过一次,这样我就不必每次调用那个对象的 save() 时都写。
还有一些数据库喜欢不同的时间格式,所以你可以在这里处理它们:
public function beforeSave() {
$this->date = date('Y-m-d', $this->date);
return parent::beforeSave();
}
如果您查看 beforeSave
的源代码,您会发现如果您的 beforeSave
没有 [=22],insertion
或 updating
进程将被取消=] true
。 "it seems like the model is saved",其实不是。
因此将您的代码调整为:
public function beforeSave($insert) {
if ($this->isAttributeChanged('name')) {
rename($this->getOldAttribute('name') . '.pdf', $this->name . '.pdf');
}
return parent::beforeSave($insert);
}
我有一个 Controller 和一个用 giiant 生成的 updateAction:
public function actionUpdate($id) {
$model = $this->findModel($id);
if ($model->load($_POST) && $model->save()) {
return $this->redirect(['view', 'id' => $model->id]);
} else {
return $this->render('update', [
'model' => $model,
]);
}
}
我想通过覆盖模型中的 beforeSave 来重命名文件:
public function beforeSave($insert) {
if ($this->isAttributeChanged('name')) {
rename($this->getOldAttribute('name') . '.pdf', $this->name . '.pdf');
}
parent::beforeSave($insert);
}
好像是保存了模型,保存后还是渲染出来的表格,怎么可能呢。我确定这是因为 beforeSave
,因为如果我将其注释掉,一切正常。 beforeSave 的使用怎么会导致这种不合逻辑的行为呢?我错过了什么?非常感谢!
Yii 和其他 MVC 框架具有这些功能。
虽然您可以在控制器中编写 "before save" 代码,但在 save() 函数之前 - 更推荐使用 beforeSave() 函数。
原因一:MVC中的M
beforeSave 与模型相关,因此在模型文件中使用处理模型属性(字段)的代码比在控制器中使用该代码更合乎逻辑。
原因 2:保存是为了插入和更新
您在插入新记录和更新现有记录时使用 save()。如果不使用 beforeSave 内置函数,您必须在保存代码之前有 2 个 "manual" 实例。 ("Waste" 代码行)
原因 3:从另一个控制器保存模型
如果你被要求扩展你的应用程序,现在你不得不面对一个需要保存相同模型的新控制器(出于某种原因 - 只是一种可能的情况) - 你将不得不将您的 "before save" 代码复制到该控制器。如果您使用的是内置的 beforeSave 函数,则不需要。
总而言之,框架的主要目的是减少您需要编写的代码,同时保持任何逻辑(MVC 分离)。虽然您可以做不同的事情,但为什么不使用已经存在的东西呢?
一个简单的例子:
我有一个带有两个日期字段的 table。每次我尝试执行插入或更新时,我都需要获取当前系统日期并根据操作类型进行操作。
public function beforeSave() {
if ($this->isNewRecord) {
$this->insertDate = new CDbExpression('NOW()');
} else {
$this->updateDate = new CDbExpression('NOW()');
}
return parent::beforeSave();
}
我写过一次,这样我就不必每次调用那个对象的 save() 时都写。
还有一些数据库喜欢不同的时间格式,所以你可以在这里处理它们:
public function beforeSave() {
$this->date = date('Y-m-d', $this->date);
return parent::beforeSave();
}
如果您查看 beforeSave
的源代码,您会发现如果您的 beforeSave
没有 [=22],insertion
或 updating
进程将被取消=] true
。 "it seems like the model is saved",其实不是。
因此将您的代码调整为:
public function beforeSave($insert) {
if ($this->isAttributeChanged('name')) {
rename($this->getOldAttribute('name') . '.pdf', $this->name . '.pdf');
}
return parent::beforeSave($insert);
}