Three Different Forms To One Table - Disable Fields

Hi. In database I have table user. There are three forms using it: RegisterForm, EditForm, AdminEditForm. Fisrt I want ask, is it correct way to do this? I want disable fields eg. username, name, surname in EditForm, because User shouldn’t change this. I tried delete it from view, but still is possible to send variable by post and hack it. How to prevent it in the best way and disable that fields?

P.s Sry for bad english, but I’m Polish. I believe you will understand my problem.

Generally, you’d use the User model directly to register or edit a user and use a CFormModel when the data is not being persisted, such as for a login form.

In your case, you’d configure scenarios in your user model, such as ‘register’, ‘edit’ and ‘adminEdit’, and you would use these in your validation rules to specify which rules apply in each scenario.

If you don’t define a rule for a specific attribute in a scenario, that attribute won’t be bulk assigned when you use $user->attributes = $_POST[‘User’], so the user won’t be able to change it.

Read carefully through the documentation about scenarios. This wiki article might also help.

Thank you! I have one question yet: there is possibility to massive attribute rules to scenario?

yes you can handle as much as you want model attributes with scenario.You just need to define proper model rules for it.

That’s not what I meant. I use word ‘attribute’ in mean like ‘join’ (stupid translator). I want do something like this:


public function rules() {

   return array( 

      array('on'=>'register',

         array('...','...'),

         array('...','...'),

         array('...','...'),

      ),

      array('on'=>'login',

         array('...','...'),

         array('...','...'),

         array('...','...'),

      )

   );

}

You structure it like this:




    array('attribute', 'rule', 'on'=>'register, edit'),

    array('name', 'required', 'except'=>'edit'), // Prevent member updating their own name

    array('name', 'length', 'max'=>20, 'except'=>'edit'), // All 'name' rules must be protected



Keith has just replied something.This what you mean.Since i was also saying the same thing here.

I have error:


method_exists() expects parameter 2 to be string, array given

site: http://test.koxu1996.linuxpl.info/site/login.html

SiteController:


$model=new UserForm('login');


		// collect user input data

		if(isset($_POST['UserForm']))

		{

			$model->attributes=$_POST['UserForm'];

			// validate user input and redirect to the previous page if valid

			if($model->validate() && $model->login())

				$this->redirect(Yii::app()->user->returnUrl);

		}

		// display the login form

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

UserForm:


<?php

class UserForm extends CFormModel {

public $id;

        public $username;

        public $password;

        public $password_real;

        public $email;

        public $code;

        public $activated;

        public $activation_key;

        public $reset_key;

        public $name;

        public $street;

        public $house_number;

        public $apartment_number;

        public $city;

        public $zip_code;

        public $phone_number;

        public $country;

        public $province;

        public $pesel;

        public $register_time;

        public $authorised_time;

        public $edit_time;

        public $saldo;

        public $referer_id;

        public $role;


        //login

        public $rememberMe;


        private $_identity;


        //register

        public $repeat_password;

        public $verifyCode;

        public $terms;


        //userEdit


        //adminEdit





        public function rules() {

            return array( 

               //login

                array(

                    array('username, password', 'required', 'on' => 'login'),

                    array('rememberMe', 'boolean', 'on' => 'login'),

                    array('password', 'authenticate', 'on' => 'login'),


                //register

                    array('username, password_real, email, name, street, house_number, apartment_number, city, zip_code, phone_number, country, province, pesel, repeat_password, verifyCode, terms', 'on' => 'register'),

                    array('username', 'unique', 'className'=>'user', 'attributeName'=>'username', 'on' => 'register'),

                    array('email','email', 'on' => 'register'),

                    array('email', 'unique', 'className'=>'user', 'attributeName'=>'email', 'on' => 'register'), 

                    array('activated','default','value'=>0,'setOnEmpty'=>false, 'on' => 'register'),  

                    array('zip_code','match', 'pattern'=>'/^[0-9]{2}-?[0-9]{3}$/Du', 'message'=>'Niepoprawny format', 'on' => 'register'),

                    array('country, province', 'numerical', 'integerOnly'=>true, 'on' => 'register'),

                    array('pesel','pesel', 'on' => 'register'),

                    array('saldo','default','value'=>0,'setOnEmpty'=>false, 'on' => 'register'),

                    array('repeat_password', 'compare', 'compareAttribute'=>'password', 'on' => 'register'),

                    array('verifyCode', 'captcha', 'allowEmpty'=>!CCaptcha::checkRequirements(), 'skipOnError'=>true, 'on' => 'register'),

                    array('terms', 'compare', 'compareValue' => true, 'message' => 'Musisz zaakceptować regulamin.', 'on' => 'register'),

                

                //userEdit    

                    array('email, name, street, house_number, apartment_number, city, zip_code, phone_number, country, province', 'on' => 'userEdit'),

                    array('zip_code','match', 'pattern'=>'/^[0-9]{2}-?[0-9]{3}$/Du', 'message'=>'Niepoprawny format', 'on' => 'userEdit'),

                    array('country, province', 'numerical', 'integerOnly'=>true, 'on' => 'userEdit'),

                    array('email','email', 'on' => 'userEdit'),

                    array('email', 'unique', 'className'=>'user', 'attributeName'=>'email', 'on' => 'userEdit'), 

                

                //adminEdit 

                    array('password_real, email, name, street, house_number, apartment_number, city, zip_code, phone_number, country, province, pesel', 'on' => 'adminEdit'),

                    array('zip_code','match', 'pattern'=>'/^[0-9]{2}-?[0-9]{3}$/Du', 'message'=>'Niepoprawny format', 'on' => 'adminEdit'),

                    array('country, province', 'numerical', 'integerOnly'=>true, 'on' => 'adminEdit'),

                    array('email', 'email', 'on' => 'adminEdit'),

                    array('email', 'unique', 'className'=>'user', 'attributeName'=>'email', 'on' => 'adminEdit'), 

                    array('pesel','pesel', 'on' => 'adminEdit'),

                

                //lostPassword 

                    array('email', 'required', 'on' => 'lostPassword'),

                    array('email', 'email', 'on' => 'lostPassword'),

                    array('email', 'checkEmail', 'on' => 'lostPassword'),

                

               

             ));

        }

}



What’s wrong?

Ahhh to much validation rules. :) lets make it simple and please try to put one by one validation rules for scenario and debug where you are doing mistake.

Also please check these links

link 1

Link 2

i hope it will help you to write model validation rule in more proper way. making attribute as a "Safe" is also a good option rather then writing this too much validation rules.

Any how i just want to say you can define these model validation rules in more simple way.

I know is possibly to make rules simpler but i will make changes and then i will must do it again.

I deleted many rules and there is only basic code and still doesnt work.

SiteController:


public function actionLogin()

	{

		$model=new UserForm('login');


		// if it is ajax validation request

		if(isset($_POST['ajax']) && $_POST['ajax']==='login-form')

		{

			echo CActiveForm::validate($model);

			Yii::app()->end();

		}


		// collect user input data

		if(isset($_POST['UserForm']))

		{

			$model->attributes=$_POST['UserForm'];

			// validate user input and redirect to the previous page if valid

			if($model->validate() && $model->login())

				$this->redirect(Yii::app()->user->returnUrl);

		}

		// display the login form

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

	}

UserForm:


<?php

class UserForm extends CFormModel {

        public $username;

        public $password;


        public $rememberMe;

        private $_identity;


        public function rules() {

            return array( 

               

                array(

                    array('username, password', 'required', 'on' => 'login'),

                    array('rememberMe', 'boolean', 'on' => 'login'),

                    array('password', 'authenticate', 'on' => 'login'),

             ));

        }


	public function authenticate($attribute,$params)

	{

		if(!$this->hasErrors())

		{

			$this->_identity=new UserIdentity($this->username,$this->password);

			if(!$this->_identity->authenticate())

				$this->addError('password','Zły login lub hasło.');

		}

	}      

}

?>

view/login.php


<?php

/* @var $this SiteController */

/* @var $model LoginForm */

/* @var $form CActiveForm  */


$this->pageTitle=Yii::app()->name . ' - Logowanie';

$this->breadcrumbs=array(

	'Logowanie',

);

?>


<h1>Logowanie</h1>


<p>Proszę wypełnić poniższy formularz danymi do logowania:</p>


<div class="form">

<?php $form=$this->beginWidget('CActiveForm', array(

	'id'=>'login-form',

	'enableClientValidation'=>true,

	'clientOptions'=>array(

		'validateOnSubmit'=>true,

	),

)); ?>


	<p class="note">Pola z <span class="required">*</span> są wymagane.</p>


	<div class="row">

		<?php echo $form->labelEx($model,'username'); ?>

		<?php echo $form->textField($model,'username'); ?>

		<?php echo $form->error($model,'username'); ?>

	</div>


	<div class="row">

		<?php echo $form->labelEx($model,'password'); ?>

		<?php echo $form->passwordField($model,'password'); ?>

		<?php echo $form->error($model,'password'); ?>

	</div>


	<div class="row rememberMe">

		<?php echo $form->checkBox($model,'rememberMe'); ?>

		<?php echo $form->label($model,'rememberMe'); ?>

		<?php echo $form->error($model,'rememberMe'); ?>

	</div>


	<div class="row buttons">

		<?php echo CHtml::submitButton('Zaloguj'); ?>

	</div>


<?php $this->endWidget(); ?>

Zapomniałeś hasła? <a href="">Kliknij tutaj!</a>

</div><!-- form -->

OMG :o :o :o :o




  public function rules() {

            return array( 

               

                array(

                    array('username, password', 'required', 'on' => 'login'),

                    array('rememberMe', 'boolean', 'on' => 'login'),

                    array('password', 'authenticate', 'on' => 'login'),

             ));

        }







public function rules() {

            return array( 

                    array('username, password', 'required', 'on' => 'login'),

                    array('rememberMe', 'boolean', 'on' => 'login'),

                    array('password', 'authenticate', 'on' => 'login'),

            );

        }



Can you see the difference in both those code above. I am pretty sure now its fix.:)

Stupid mistake :confused: Now i have problem with summing all prices in relation. Site shows error:


Active record "Payment" is trying to select an invalid column "SUM(price)". Note, the column must exist in the table or be an expression with alias.

relation:


'price_sum' => array(self::HAS_MANY,'Payment','user_id','select'=> "SUM(price)",'condition'=>"type='2'")

cgrid view:


...

'header' => 'Sum prices',

'name' => 'price_sum',

'type' => 'raw',

'htmlOptions'=>array('style'=>'text-align: center'),

...

But there is field price in database. What can be wrong?

Instead of this i will suggest you to create a getter method in model class and call it in CgridView.