In my application i've a model called User Where i've implemented a scenario for validations.
const SCENARIO_RESET_PASSWORD = 'passwordReset';
public function rules()
{
return[
[['name','surname','password','username','id_role'], 'required'],
[['email','email2'], 'email'],
[['username','email'], 'unique'],
['confirmPassword', 'compare', 'compareAttribute'=>'password', 'on' => self::SCENARIO_RESET_PASSWORD]
];
}
With this configuration i can create a new User, delete one and update all fields except for 'password'.
This is the action in my controller:
public function actionUpdate($id)
{
$user = User::findOne($id);
if($user->load(Yii::$app->request->post())&& $user->validate()) {
$user->update();
$this->redirect(\yii\helpers\Url::toRoute('index'));
}
return $this->render('update',[
'user' => $user,
]);
}
i've already checked that the field 'password' is passed on post parameters with success.
and this is my view:
<h1> Edit User </h1>
<?php
$form = ActiveForm::begin([
'id' => 'active-form',
'options' => [
'class' => 'form-horizontal',
'enctype' => 'multipart/form-data'
],
]);
?>
<?= $form->errorSummary($user); ?>
<?= $form->field($user, 'name') ?>
<?= $form->field($user, 'surname') ?>
<?= $form->field($user, 'username') ?>
<?= $form->field($user, 'email') ?>
<?= $form->field($user, 'password')->passwordInput() ?>
<?php if(Yii::$app->user->identity->id_role === User::USER_ADMIN): ?>
<?= $form->field($user, 'id_role')->dropDownList(
Role::find()->select(['name','id'])->indexBy('id')->column(),
['prompt'=>'Select a role']
);
?>
<?php endif; ?>
<div class="form-group">
<?= Html::submitButton('Save the user', ['class' => 'btn btn-success']) ?>
</div>
<?php ActiveForm::end(); ?>
I really don't know why i'm getting this error
Please remove
'on' => self::SCENARIO_RESET_PASSWORD
or
define your SCENARIO in your controller action as
$user->scenario = 'SCENARIO_RESET_PASSWORD';
Related
Hellow i'm making several forms and their validation on YII with ajax and i have some problems
Here the view code:
<?
$form = ActiveForm::begin([
'id' => 'test-form',
'options' => ['class' => 'form-horizontal'],
]) ?>
<?= $form->field($model, 'name')->textInput(['placeholder' => "Имя"])->label('Имя'); ?>
<?= $form->field($model, 'lastname')->textInput(['placeholder' => "Фамилия"])->label('Фамилия'); ?>
<?= $form->field($model, 'country')->textInput(['placeholder' => "Страна"])->label('Страна'); ?>
<?= $form->field($model, 'pindex')->textInput(['placeholder' => "Индекс"])->label('Индекс'); ?>
<?= $form->field($model, 'card') ->textInput(['placeholder' => "Ваш номер карты xxxx xxxx xxxx xxxx"])->label('Номер карты');?>
<?= $form->field($model, 'form_name')->hiddenInput(['value' => 'Form']) ?>
<div class="form-group">
<div class="">
<?= Html::submitButton('Отправить', ['class' => 'btn btn-primary']) ?>
</div>
</div>
<?php ActiveForm::end() ?>
<?
$form = ActiveForm::begin([
'id' => 'mobile-form',
'options' => ['class' => 'form-horizontal'],
]) ?>
<?= $form->field($model2, 'name')->textInput(['placeholder' => "Имя"])->label('Имя'); ?>
<?= $form->field($model2, 'lastname')->textInput(['placeholder' => "Фамилия"])->label('Фамилия'); ?>
<?= $form->field($model2, 'country')->textInput(['placeholder' => "Страна"])->label('Страна'); ?>
<?= $form->field($model2, 'pindex')->textInput(['placeholder' => "Индекс"])->label('Индекс'); ?>
<?= $form->field($model2, 'phone') ->textInput(['placeholder' => "Ваш телефон"])->label('Ваш телефон');?>
<?= $form->field($model2, 'form_name')->hiddenInput(['value' => 'Mobile']) ?>
<div class="form-group">
<div class="">
<?= Html::submitButton('Отправить', ['class' => 'btn btn-primary']) ?>
</div>
</div>
<?php ActiveForm::end() ?>
Then im sending data with ajax to controller, code:
namespace app\controllers;
use Yii;
use yii\filters\AccessControl;
use yii\web\Controller;
use yii\web\Response;
use yii\filters\VerbFilter;
use app\models\MainForm;
use app\models\EntryForm;
use app\models\EntryMobile;
class SiteController extends Controller
{
/**
* {#inheritdoc}
*/
public function actionEntry(){
$model = new EntryForm;
$model2 = new EntryMobile;
if(Yii::$app->request->isAjax) {
$model->load(Yii::$app->request->post());
$model2->load(Yii::$app->request->post());
if($model->validate() || $model2->validate()){
$json['ok'] = "";
}else{
$json['error'] = " ";
}
Yii::$app->response->format = Response::FORMAT_JSON;
return $json;
} else {
return $this->render('entry', ['model' => $model,'model2' => $model2]);
}
}
In models i have MainForm , and EntryForm and EntryMobile that extends MainForm with their own rules.
Here is a question:
How to make $model->validation() and $model2->validation() in one method? Or how to make the controller method width on model for two forms. Scenarios doesnt work cause they made me make the same. Two object and etc. Please help
You can use bitwise and for testing both models validations. Like:
$model->validate() & $model2->validate()
Which will then proceed only if both conditions are true but will test both of them anyway (which should throw the validation errors you expect to see).
I am trying to use the code I found very well explained in this post How to create a Yii2 model without a database , but it gives me the Unknown property error : "Gettting unknown property: app...\DBcomponents::newhost" .
Maybe I am using wrong the Model class. Could anyone please explain to me what is the problem? Thank you!
Here you have the code:
The view:
div class="db-create">
<h1><?= Html::encode($this->title) ?></h1>
<?= $this->render('_db', [
// the model is DBcomponents
'model' => $model,
]) ?>
</div>
The form:
<div class="db-form">
<?php $form = ActiveForm::begin(); ?>
<?= $form->field($model, 'newhost')->textInput(['maxlength' => true]) ?>
<?= $form->field($model, 'dbname')->textInput() ?>
<?= $form->field($model, 'username')->textInput(['maxlength' => true])?>
<?= $form->field($model, 'password')->textInput() ?>
<div class="form-group">
<?= Html::submitButton( 'Connect', ['class' =>'btn btn-primary']) ?>
</div>
<?php ActiveForm::end(); ?>
</div>
And the model:
class DBcomponents extends \yii\base\Model
{/**
* #inheritdoc
*/
public function rules()
{
return [
[['username', 'password','newhost','dbname',], 'required'],
[['username', 'password','newhost','dbname',], 'string', 'max'=> 100],
];
}
/**
* #inheritdoc
*/
public function attributeLabels()
{
return [
'username' => 'username',
'password' => 'password',
'newhost' => 'newhost',
'dbname' => 'dbname',
];
}}
As #yafater suggested I set the variables public and it soleved the problem. Thank you
In frontend of Yii ,
I have 2 form :
1 Login Form
2 Signup
my signup form is working , but when login is not working ,
i found a error
Call to a member function formName() on null
//Form Code
<!-------signup---------->
<h1>Signup Form</h1>
<?php $form = ActiveForm::begin(['id' => 'form-signup', 'action' => Url::to(['site/signup'])]); ?>
<?= $form->field($modelSignup, 'username')->textInput(['autofocus' => true]) ?>
<?= $form->field($modelSignup, 'email') ?>
<?= $form->field($modelSignup, 'password')->passwordInput() ?>
<?= Html::submitButton('Signup', ['class' => 'btn btn-primary', 'name' => 'signup-button']) ?>
<?php ActiveForm::end(); ?>
<!-------// signup---------->
<!-------login---------->
<h1>Login Form</h1>
<?php $form = ActiveForm::begin(['id' => 'form-login', 'action' => Url::to(['site/login'])]); ?>
<?= $form->field($modelLogin, 'username')->textInput(['autofocus' => true]) ?>
<?= $form->field($modelLogin, 'email') ?>
<?= $form->field($modelLogin, 'password')->passwordInput() ?>
<?= Html::submitButton('Login', ['class' => 'btn btn-primary', 'name' => 'login-button']) ?>
<?php ActiveForm::end(); ?>
<!-------//login---------->
Try this:
Controller:
public function actionIndex() {
$modelSignup = new SignupForm();
$modelLogin = new LoginForm();
return $this->render('index',[ 'modelSignup' => $modelSignup,'modelLogin' => $modelLogin ]);
}
Also remove this check from your code:
if(isset($modelLogin)
In your view file you are using two models, one for signup and the other for login. But from your comment I had note that you are passing only one model at a time it may be the first one or the second one. So you should replace your actionIndex() with the following code:
public function actionIndex() {
$modelSignup = new SignupForm();
$modelLogin = new LoginForm();
if(isset($_POST['SignupForm'])) {
//code for signup process
}
if(isset($_POST['LoginForm'])) {
//code for login process
}
return $this->render('index', [ 'modelSignup' => $modelSignup, 'modelLogin' => $modelLogin ]);
}
This will help you.
I'm new to CakePhp framework and followed the blog tutorial.
Everything went smooth until authentication part.
The following two lines were the problem:
<?= $this->Form->input('Usuario') ?>
<?= $this->Form->input('Contraseña') ?>
The correct lines are:
<?= $this->Form->input('username') ?>
<?= $this->Form->input('password') ?>
This is my login method from UsersControllers.php, the debug line always returns false.
public function login()
{
if ($this->request->is('post')) {
debug($this->Auth->identify());
$user = $this->Auth->identify();
if ($user) {
$this->Auth->setUser($user);
return $this->redirect($this->Auth->redirectUrl());
}
$this->Flash->error(__('Usuario o contraseña inválida, intente nuevamente'));
}
}
This is my user class
I had to change the line protected $_accessible = ['*' => true]; as appears in the tutorial, otherwise users wouldn't be saved.
class User extends Entity
{
// Make all fields mass assignable for now.
protected $_accessible = ['username' => true,'password'=>true,'role'=>true,'created'=>true,'modified'=>true];
// ...
protected function _setPassword($password)
{
return (new DefaultPasswordHasher)->hash($password);
}
// ...
}
This is my login.ctp
<div class="users form">
<?= $this->Flash->render('auth') ?>
<?= $this->Form->create() ?>
<fieldset>
<legend><?= __('Ingrese su usuario y contraseña') ?></legend>
<?= $this->Form->input('Usuario') ?>
<?= $this->Form->input('Contraseña') ?>
</fieldset>
<?= $this->Form->button(__('Login')); ?>
<?= $this->Form->end() ?>
</div>
These are my AppController.php methods:
public function initialize()
{
$this->loadComponent('Flash');
$this->loadComponent('Auth', [
'loginRedirect' => [
'controller' => 'Expedientes',
'action' => 'index'
],
'logoutRedirect' => [
'controller' => 'Pages',
'action' => 'display',
'home'
]
]);
}
public function beforeFilter(Event $event)
{
$this->Auth->allow(['index', 'view']);
}
At this point I can add users, their passwords are hashed but I can't login.
Any help will be greatly appreciated.
Thanks in advance.
Alternatively, while setting your Auth componenent configurations, you can set which fields, in your db, serve as username and password
$this->Auth->config('authenticate', [
'Form' => [
'fields' => [
'username'=>'email',
'password' => 'password'
],
'userModel' => 'Users'
]
]);
Thanks #ndm for the answer. I translated username and password fields in the following lines:
<?= $this->Form->input('Usuario') ?>
<?= $this->Form->input('Contraseña') ?>
Correct lines are:
<?= $this->Form->input('username') ?>
<?= $this->Form->input('password ') ?>
I want to get multiplie instance of the same model in my controller. I saw this wiki for Yii 1.1 and tried like that but in my code only last instance in form was acceble from controller my code is here (I commented code with error and variable values):
$model = new Person(['scenario' => 'create_update']);
$contractDate = new DatePart(); // DatePart is my own class
$contractExpirationDate = new DatePart(); // DatePart is my own class
if ($model->load(Yii::$app->request->post()) &&
$contractDate->load(Yii::$app->request->post()) &&
$contractExpirationDate->load(Yii::$app->request->post())){
Yii::info(Yii::$app->request->post(),'test'); // only one instance of Person and one instance of DatePart are available here
Yii::info($_POST['DatePart'],'test'); // only last instance of DatePart (contractExpirationDate in html form) is available here
Yii::info($_POST['DatePart'][0],'test'); // Error: Undefined offset: 0
Yii::info($_POST['DatePart'][1],'test'); // Error: Undefined offset: 1
$model->save();
return $this->redirect(['view', 'id' => $model->id]);
} else {
return $this->render('create', [
'model' => $model,
'contractDate' => $contractDate,
'contractExpirationDate' => $contractExpirationDate,
]);
}
It is my form view in _form.php:
<?php
use yii\helpers\Html;
//use yii\widgets\ActiveForm;
use kartik\widgets\ActiveForm;
use common\models\DataOperations;
/* #var $this yii\web\View */
/* #var $model app\models\Person */
/* #var $contractDate backend\viewModels\DatePart */
/* #var $contractExpirationDate backend\viewModels\DatePart */
/* #var $form yii\widgets\ActiveForm */
?>
<div class="user-form">
<?php
$form = kartik\widgets\ActiveForm::begin(
[
'id' => $model->isNewRecord ? 'user-form-create' : 'user-form-update',
'type' => ActiveForm::TYPE_VERTICAL,
//'enableAjaxValidation' => true,
'fieldConfig' => [
//'autoPlaceholder'=>true
]
]);
?>
<?= $form->field($model, 'name')->textInput(['maxlength' => 60]) ?>
<?= $form->field($model, 'family')->textInput(['maxlength' => 60]) ?>
<?= $form->field($model, 'mobile')->textInput() ?>
<?= $form->field($contractDate, 'year')->textInput() ?>
<?= $form->field($contractDate, 'month')->textInput() ?>
<?= $form->field($contractDate, 'day')->textInput() ?>
<?= $form->field($contractExpirationDate, 'year')->textInput() ?>
<?= $form->field($contractExpirationDate, 'month')->textInput() ?>
<?= $form->field($contractExpirationDate, 'day')->textInput() ?>
<div class="form-group">
<?= Html::submitButton($model->isNewRecord ? Yii::t('app', 'Create') : Yii::t('app', 'Update'), ['class' => $model->isNewRecord ? 'btn btn-success' : 'btn btn-primary']) ?>
</div>
<?php ActiveForm::end(); ?>
</div>
It is log result for:
Yii::info(Yii::$app->request->post(),'test')
in debugger as you seen only last DatePart available but I have two DatePart model instance (contractDate and contractExpirationDate):
[
'_csrf' => 'Vl81R0ZvMk1hD1oELT9aDzkIe3EPHFgiIBJTBhA9RD8GbFM.AhlVBw==',
'Person' => [
'name' => 'test name',
'family' => 'test family',
'mobile' => '09121212123',
],
'DatePart' => [
'year' => '2015',
'month' => 'Jun',
'day' => 'Mon',
],
]
Controller:
$model = new Person(['scenario' => 'create_update']);
$dates = [
'contractDate' => new DatePart(),
'contractExpirationDate' => new DatePart()
];
if ($model->load(Yii::$app->request->post())) {
if (Model::loadMultiple($dates, Yii::$app->request->post()) && Model::validateMultiple($dates)) {
foreach ($dates as $date) {
$date->save();
}
// or
$contractDate = $dates['contractDate'];
$contractExpirationDate = $dates['contractExpirationDate'];
// ...... some logic
$model->save();
return $this->redirect(['view', 'id' => $model->id]);
}
}
else {
return $this->render('create', [
'model' => $model,
'dates' => $dates
]);
}
View Form:
<?= $form->field($dates, '[contractDate]year')->textInput() ?>
<?= $form->field($dates, '[contractDate]month')->textInput() ?>
<?= $form->field($dates, '[contractDate]day')->textInput() ?>
<?= $form->field($dates, '[contractExpirationDate]year')->textInput() ?>
<?= $form->field($dates, '[contractExpirationDate]month')->textInput() ?>
<?= $form->field($dates, '[contractExpirationDate]day')->textInput() ?>
To complement b24 answer.
// In View Form add foreach:
<?php foreach ($dates as $index => $date): ?>
<?= $form->field($date, '[contractDate]year')->textInput() ?>
<?= $form->field($date, '[contractDate]month')->textInput() ?>
<?= $form->field($date, '[contractDate]day')->textInput() ?>
<?= $form->field($date, '[contractExpirationDate]year')->textInput() ?>
<?= $form->field($date, '[contractExpirationDate]month')->textInput() ?>
<?= $form->field($date, '[contractExpirationDate]day')->textInput() ?>
<?php endforeach; ?>
// - or - add index
<?= $form->field($dates['contractDate'], '[contractDate]year')->textInput() ?>
<?= $form->field($dates['contractDate'], '[contractDate]month')->textInput() ?>
<?= $form->field($dates['contractDate'], '[contractDate]day')->textInput() ?>
<?= $form->field($dates['contractExpirationDate'], '[contractExpirationDate]year')->textInput() ?>
<?= $form->field($dates['contractExpirationDate'], '[contractExpirationDate]month')->textInput() ?>
<?= $form->field($dates['contractExpirationDate'], '[contractExpirationDate]day')->textInput() ?>
This can be is solution for this problem :
http://www.yiiframework.com/forum/index.php/topic/53935-solved-subforms/page__p__248184#entry248184