9

在此处输入图像描述

我不想更新密码字段。如何使用它。我使用 md5 编码作为密码。所以我不想更新 yii 框架中的密码字段。任何帮助表示赞赏?

4

6 回答 6

7

我认为更好的方法是在这种情况下不使用该场景。规则中的下一个代码只是对场景说:下一个字段是必需的。但不是:跳过另一个 else

array('name, username, email', 'required', 'on' => 'update'),

例如,如果我们将密码长度限制为最多 32 个字符,但在数据库中以 sha1 格式存储(长度为 40),那么我们就会遇到问题,因为验证器会阻塞数据库查询。这是因为当您进行更新时,“validatе”方法检查所有类属性(关于数据库表映射),而不仅仅是邮寄的新属性。

可以使用方法“saveAttributes”,但后来我注意到另一个问题。如果“email”列在数据库中是唯一的,并且如果编辑的电子邮件与现有的电子邮件重复,则规则中定义的 Yii 消息系统无法通知并抛出有关数据库查询的错误代码。

我认为最简单的方法是:在这种情况下不要设置场景。只需将您想要的属性作为参数发送。这将保留 GII 创建的所有 CRUD 功能。

在您的代码中,它看起来像这样:(在模型中)

public function rules() {
    return array(
        array('name, username, email, password', 'required'),
    );
}

(在控制器中)

if($id==Yii::app()->user->id){ 
    $model=$this->loadModel($id); 
    if(isset($_POST['JbJsJobResume'])) { 
        $model->attributes=$_POST['JbJsJobResume']; 
        if($model->save(true, array('name', 'username', 'email'))) 
            $this->redirect(array('view','id'=>$model->id)); 
    } 

    $this->render('update',array( 'model'=>$model, )); 
}

我注意到您不使用 RBAC。它非常方便和灵活 - 试试吧。

http://www.yiiframework.com/doc/guide/1.1/en/topics.auth#role-based-access-control

于 2013-07-21T02:58:34.903 回答
5

在您的模型中,您必须执行以下操作:

public function rules() {
    return array(
        array('name, username, email, password', 'required', 'on' => 'create'),
        array('name, username, email', 'required', 'on' => 'update'),
    );
}

假设您现在运行的场景是更新。所以我不需要那里的密码。我只在您可能拥有的创建场景中需要它。因此,在您拥有的视图文件中删除密码字段并在您拥有的操作中包含以下内容:

$model->setScenario('update');

所以它不需要密码,它会保持不变。

对于密码更改,您可以创建一个新操作(例如 actionPassChange),您需要在其中输入两次新密码。

于 2012-11-23T10:48:07.157 回答
2
$model->attributes=$_POST['JbJsJobResume'];

而不是分配所有属性,只需分配您想要保存的属性,如

$model->name=$_POST['JbJsJobResume']['name'];
$model->save();
于 2012-11-23T11:15:58.720 回答
1

我不确定为什么这是一个问题,一些代码可以帮助我们理解原因。如果您不希望捕获/更新密码,那么为什么表单中有密码字段?

如果您从视图中删除密码字段,密码字段的值将不会被发送回控制器,然后它不会被更新。

上述方法有可能不起作用,这可能是在您的用户模型中,您正在加密afterValidate方法中的密码?:

protected function afterValidate()
{
    parent::afterValidate();
    $this->password = $this->encrypt($this->password);
}

public function encrypt($value)
{
    return md5($value);
}

在这种情况下,如果您从视图中删除密码字段,而只是更新名称、用户名或电子邮件,那么密码的 md5 哈希将自动重新哈希,您将丢失真实密码。

解决此问题的一种方法是在 afterValidate 方法(创建或更新)中对密码进行 md5 验证,但是如果用户希望以相同的形式更改配置文件详细信息,请要求用户再次验证其密码。

  1. FORM:用户更改名称并验证密码
  2. 已发布表格
  3. 控制器调用认证方法。
  4. 如果验证为真,覆盖用户表中的条目(包括验证密码)
于 2013-07-21T21:18:36.250 回答
1

第一个选项只需在设置密码字段之前取消设置:

function update(){
    $model=$this->loadModel($id);
    unset($_POST['JbJsJobResume']['password']);
    $model->attributes=$_POST['JbJsJobResume'];
    $model->save();  
}

第二个选项:使用临时变量:

function update(){
    $model=$this->loadModel($id);
    $temPassword = $model->passwrod;
    $model->attributes=$_POST['JbJsJobResume'];
    $model->passwrod = $temPassword;
    $model->save();  
}

第三种选择:使用场景

于 2013-07-21T03:40:59.613 回答
-1

我认为@Gravy 的回答是正确的,谢谢 Gravy 和 Nikos Tsirakis。我已经修复了与@faizphp 几乎相同的问题。正如 Nikos Tsirakis 所说,我为用户模型添加了场景,但也遇到了同样的问题。然后我发现我在User.afterValidate中加密了密码,所以每次更新用户模型时,程序再次将数据库中的密码加密为错误的密码。所以我改变了我的功能

protected function afterValidate()
{
        parent::afterValidate();
        if (!$this->hasErrors())
            $this->password = $this->hashPassword($this->password);
}
</code>



protected function afterValidate()
{
        parent::afterValidate();
        if (!$this->hasErrors() && $this->scenario==="create")
            $this->password = $this->hashPassword($this->password);
}

. 这似乎工作。

于 2013-07-31T10:57:21.820 回答