Autentificación de usuarios

git-svn-id: https://192.168.0.254/svn/Proyectos.Incam_IntranetNueva/trunk@9 77cfc57b-8ef4-1849-9df6-4a38aa5da120
This commit is contained in:
David Arranz 2012-02-01 15:41:14 +00:00
parent d74960182b
commit d2c5a8b6b4
18 changed files with 565 additions and 30 deletions

View File

@ -7,27 +7,38 @@
*/
class UserIdentity extends CUserIdentity
{
/**
* Authenticates a user.
* The example implementation makes sure if the username and password
* are both 'demo'.
* In practical applications, this should be changed to authenticate
* against some persistent user identity storage (e.g. database).
* @return boolean whether authentication succeeds.
*/
public function authenticate()
{
$users=array(
// username => password
'demo'=>'demo',
'admin'=>'admin',
);
if(!isset($users[$this->username]))
$this->errorCode=self::ERROR_USERNAME_INVALID;
else if($users[$this->username]!==$this->password)
$this->errorCode=self::ERROR_PASSWORD_INVALID;
else
$this->errorCode=self::ERROR_NONE;
return !$this->errorCode;
}
private $_id;
/**
* Authenticates a user.
* @return boolean whether authentication succeeds.
*/
public function authenticate()
{
$user = Usuario::model()->findByAttributes(array('username'=>$this->username));
if ($user === NULL) {
$this->errorCode = self::ERROR_USERNAME_INVALID;
}
else {
if ($user->password !== $user->encrypt($this->password)) {
$this->errorCode = self::ERROR_PASSWORD_INVALID;
}
else {
$this->_id = $user->id;
if ($user->last_login_time === null) {
$lastLogin = time();
} else {
$lastLogin = strtotime($user->last_login_time);
$this->setState('lastLoginTime', $lastLogin);
}
$this->errorCode = self::ERROR_NONE;
}
}
return !$this->errorCode;
}
public function getId() {
return $this->_id;
}
}

View File

@ -0,0 +1,176 @@
<?php
class UsuarioController extends Controller
{
/**
* @var string the default layout for the views. Defaults to '//layouts/column2', meaning
* using two-column layout. See 'protected/views/layouts/column2.php'.
*/
public $layout='//layouts/column2';
/**
* @return array action filters
*/
public function filters()
{
return array(
'accessControl', // perform access control for CRUD operations
);
}
/**
* Specifies the access control rules.
* This method is used by the 'accessControl' filter.
* @return array access control rules
*/
public function accessRules()
{
return array(
array('allow', // allow all users to perform 'index' and 'view' actions
'actions'=>array('index','view'),
'users'=>array('*'),
),
array('allow', // allow authenticated user to perform 'create' and 'update' actions
'actions'=>array('create','update'),
'users'=>array('@'),
),
array('allow', // allow admin user to perform 'admin' and 'delete' actions
'actions'=>array('admin','delete'),
'users'=>array('admin'),
),
array('deny', // deny all users
'users'=>array('*'),
),
);
}
/**
* Displays a particular model.
* @param integer $id the ID of the model to be displayed
*/
public function actionView($id)
{
$this->render('view',array(
'model'=>$this->loadModel($id),
));
}
/**
* Creates a new model.
* If creation is successful, the browser will be redirected to the 'view' page.
*/
public function actionCreate()
{
$model=new Usuario;
// Uncomment the following line if AJAX validation is needed
// $this->performAjaxValidation($model);
if(isset($_POST['Usuario']))
{
$model->attributes=$_POST['Usuario'];
if($model->save())
$this->redirect(array('view','id'=>$model->id));
}
$this->render('create',array(
'model'=>$model,
));
}
/**
* Updates a particular model.
* If update is successful, the browser will be redirected to the 'view' page.
* @param integer $id the ID of the model to be updated
*/
public function actionUpdate($id)
{
$model=$this->loadModel($id);
// Uncomment the following line if AJAX validation is needed
// $this->performAjaxValidation($model);
if(isset($_POST['Usuario']))
{
$model->attributes=$_POST['Usuario'];
if($model->save())
$this->redirect(array('view','id'=>$model->id));
}
$this->render('update',array(
'model'=>$model,
));
}
/**
* Deletes a particular model.
* If deletion is successful, the browser will be redirected to the 'admin' page.
* @param integer $id the ID of the model to be deleted
*/
public function actionDelete($id)
{
if(Yii::app()->request->isPostRequest)
{
// we only allow deletion via POST request
$this->loadModel($id)->delete();
// if AJAX request (triggered by deletion via admin grid view), we should not redirect the browser
if(!isset($_GET['ajax']))
$this->redirect(isset($_POST['returnUrl']) ? $_POST['returnUrl'] : array('admin'));
}
else
throw new CHttpException(400,'Invalid request. Please do not repeat this request again.');
}
/**
* Lists all models.
*/
public function actionIndex()
{
$dataProvider=new CActiveDataProvider('Usuario');
$this->render('index',array(
'dataProvider'=>$dataProvider,
));
}
/**
* Manages all models.
*/
public function actionAdmin()
{
$model=new Usuario('search');
$model->unsetAttributes(); // clear any default values
if(isset($_GET['Usuario']))
$model->attributes=$_GET['Usuario'];
$this->render('admin',array(
'model'=>$model,
));
}
/**
* Returns the data model based on the primary key given in the GET variable.
* If the data model is not found, an HTTP exception will be raised.
* @param integer the ID of the model to be loaded
*/
public function loadModel($id)
{
$model=Usuario::model()->findByPk($id);
if($model===null)
throw new CHttpException(404,'The requested page does not exist.');
return $model;
}
/**
* Performs the AJAX validation.
* @param CModel the model to be validated
*/
protected function performAjaxValidation($model)
{
if(isset($_POST['ajax']) && $_POST['ajax']==='usuario-form')
{
echo CActiveForm::validate($model);
Yii::app()->end();
}
}
}

View File

@ -16,6 +16,10 @@ class m120127_152205_tbl_candidatos extends CDbMigration
'sexo' => 'string',
'fecha_nacimiento' => 'date',
'lugar_nacimiento' => 'string',
'fecha_alta' => 'datetime',
'usuario_alta' => 'integer',
'fecha_modificacion' => 'datetime',
'usuario_modificacion' => 'integer',
));
}

View File

@ -147,4 +147,19 @@ class Candidato extends CActiveRecord
'criteria'=>$criteria,
));
}
protected function beforeValidate() {
if ($this->isNewRecord) {
$this->fecha_alta = date('Y-m-d H:i:s', time());
$this->fecha_modificacion = $this->fecha_alta;
$this->usuario_alta = Yii::app()->user->id;
$this->usuario_modificacion = Yii::app()->user->id;
}
else {
$this->fecha_modificacion = date('Y-m-d H:i:s', time());
$this->usuario_modificacion = Yii::app()->user->id;
}
return parent::beforeValidate();
}
}

View File

@ -69,6 +69,7 @@ class LoginForm extends CFormModel
{
$duration=$this->rememberMe ? 3600*24*30 : 0; // 30 days
Yii::app()->user->login($this->_identity,$duration);
Usuario::model()->updateByPk($this->_identity->id, array('last_login_time' => date('Y-m-d H:i:s', time())));
return true;
}
else

View File

@ -13,6 +13,9 @@
*/
class Usuario extends CActiveRecord
{
public $password_repeat;
/**
* Returns the static model of the specified AR class.
* @param string $className active record class name.
@ -39,9 +42,11 @@ class Usuario extends CActiveRecord
// NOTE: you should only define rules for those attributes that
// will receive user inputs.
return array(
array('username, password', 'required'),
array('password', 'compare'), // el 'compare' busca otra propiedad que se llame 'password' + '_repeat'
array('password_repeat', 'safe'),
array('email, username, password, password_repeat', 'required'),
array('email, name, username, password', 'length', 'max'=>255),
array('last_login_time', 'safe'),
array('email, username', 'unique'),
// The following rule is used by search().
// Please remove those attributes that should not be searched.
array('id, email, name, username, password, last_login_time', 'safe', 'on'=>'search'),
@ -70,6 +75,7 @@ class Usuario extends CActiveRecord
'name' => 'Nombre',
'username' => 'Usuario',
'password' => 'Contraseña',
'password_repeat' => 'Confirmar contraseña',
'last_login_time' => 'Último acceso',
);
}
@ -96,4 +102,13 @@ class Usuario extends CActiveRecord
'criteria'=>$criteria,
));
}
}
protected function afterValidate() {
parent::afterValidate();
$this->password = $this->encrypt($this->password);
}
public function encrypt($value) {
return md5($value);
}
}

View File

@ -2,3 +2,48 @@
in C:\Intranet\www\index.php (13)
2012/01/30 11:56:20 [error] [system.db.CDbCommand] CDbCommand::fetchAll() failed: SQLSTATE[42S02]: Base table or view not found: 1146 Table 'intranet_dev.tbl_capacidades_candidatos' doesn't exist. The SQL statement executed was: SHOW COLUMNS FROM `tbl_capacidades_candidatos`.
in C:\Intranet\www\index.php (13)
2012/02/01 09:52:54 [error] [exception.CException] exception 'CException' with message 'Property "Usuario.password_repeat_repeat" is not defined.' in C:\Intranet\yii\framework\base\CComponent.php:131
Stack trace:
#0 C:\Intranet\yii\framework\db\ar\CActiveRecord.php(144): CComponent->__get('password_repeat...')
#1 C:\Intranet\yii\framework\validators\CCompareValidator.php(91): CActiveRecord->__get('password_repeat...')
#2 C:\Intranet\yii\framework\validators\CValidator.php(197): CCompareValidator->validateAttribute(Object(Usuario), 'password_repeat')
#3 C:\Intranet\yii\framework\base\CModel.php(158): CValidator->validate(Object(Usuario), NULL)
#4 C:\Intranet\yii\framework\db\ar\CActiveRecord.php(786): CModel->validate(NULL)
#5 C:\Intranet\www\protected\controllers\UsuarioController.php(72): CActiveRecord->save()
#6 C:\Intranet\yii\framework\web\actions\CInlineAction.php(50): UsuarioController->actionCreate()
#7 C:\Intranet\yii\framework\web\CController.php(309): CInlineAction->runWithParams(Array)
#8 C:\Intranet\yii\framework\web\filters\CFilterChain.php(134): CController->runAction(Object(CInlineAction))
#9 C:\Intranet\yii\framework\web\filters\CFilter.php(41): CFilterChain->run()
#10 C:\Intranet\yii\framework\web\CController.php(1146): CFilter->filter(Object(CFilterChain))
#11 C:\Intranet\yii\framework\web\filters\CInlineFilter.php(59): CController->filterAccessControl(Object(CFilterChain))
#12 C:\Intranet\yii\framework\web\filters\CFilterChain.php(131): CInlineFilter->filter(Object(CFilterChain))
#13 C:\Intranet\yii\framework\web\CController.php(292): CFilterChain->run()
#14 C:\Intranet\yii\framework\web\CController.php(266): CController->runActionWithFilters(Object(CInlineAction), Array)
#15 C:\Intranet\yii\framework\web\CWebApplication.php(276): CController->run('create')
#16 C:\Intranet\yii\framework\web\CWebApplication.php(135): CWebApplication->runController('usuario/create')
#17 C:\Intranet\yii\framework\base\CApplication.php(162): CWebApplication->processRequest()
#18 C:\Intranet\www\index.php(13): CApplication->run()
#19 {main}
REQUEST_URI=/intranet/index.php?r=usuario/create
HTTP_REFERER=http://localhost/intranet/index.php?r=usuario/create
---
2012/02/01 10:12:49 [error] [php] include(Ususario.php) [<a href='function.include'>function.include</a>]: failed to open stream: No such file or directory (C:\Intranet\yii\framework\YiiBase.php:418)
Stack trace:
#0 C:\Intranet\www\protected\components\UserIdentity.php(18): spl_autoload_call()
#1 C:\Intranet\www\protected\models\LoginForm.php(52): UserIdentity->authenticate()
#2 C:\Intranet\yii\framework\validators\CInlineValidator.php(43): LoginForm->authenticate()
#3 C:\Intranet\yii\framework\validators\CValidator.php(197): CInlineValidator->validateAttribute()
#4 C:\Intranet\yii\framework\base\CModel.php(158): CInlineValidator->validate()
#5 C:\Intranet\www\protected\controllers\SiteController.php(88): LoginForm->validate()
#6 C:\Intranet\yii\framework\web\actions\CInlineAction.php(50): SiteController->actionLogin()
#7 C:\Intranet\yii\framework\web\CController.php(309): CInlineAction->runWithParams()
#8 C:\Intranet\yii\framework\web\CController.php(287): SiteController->runAction()
#9 C:\Intranet\yii\framework\web\CController.php(266): SiteController->runActionWithFilters()
#10 C:\Intranet\yii\framework\web\CWebApplication.php(276): SiteController->run()
#11 C:\Intranet\yii\framework\web\CWebApplication.php(135): CWebApplication->runController()
#12 C:\Intranet\yii\framework\base\CApplication.php(162): CWebApplication->processRequest()
#13 C:\Intranet\www\index.php(13): CWebApplication->run()
REQUEST_URI=/intranet/index.php?r=site/login
in C:\Intranet\www\protected\components\UserIdentity.php (18)
in C:\Intranet\www\protected\models\LoginForm.php (52)
in C:\Intranet\www\protected\controllers\SiteController.php (88)

View File

@ -0,0 +1,5 @@
<?php
return array (
'template' => 'default',
'baseControllerClass' => 'Controller',
);

View File

@ -4,6 +4,7 @@ class CandidatoTest extends CDbTestCase {
public $fixtures = array(
'datos_candidatos' => 'Candidato',
'datos_usuarios' => 'Usuario',
);
@ -14,15 +15,17 @@ class CandidatoTest extends CDbTestCase {
}
public function testCreate() {
$candidato = $this->datos_candidatos('candidato1');
$candidato = new Candidato();
Yii::app()->user->setId($this->datos_usuarios('user1')->id);
$this->assertTrue($candidato instanceof Candidato);
$candidato->nombre = 'Juan';
$this->assertTrue($candidato->save());
$guardado = Candidato::model()->findByPk($candidato->id);
$this->assertTrue($guardado instanceof Candidato);
$this->assertEmpty(array_diff($guardado->attributes, $candidato->attributes));
$this->assertEmpty(array_diff($candidato->attributes, $guardado->attributes));
$this->assertEquals(Yii::app()->user->id, $guardado->usuario_alta);
}
public function testUpdate() {

View File

@ -58,5 +58,16 @@ class CapacidadIdiomaTest extends CDbTestCase {
$this->assertEquals(1, count($idiomas));
$this->assertEquals($this->datos_idiomas['idioma2']['idioma'], $idiomas[0]->idioma);
}
public function testWith() {
$id = $this->datos_candidatos['candidato3']['id'];
$candidato = Candidato::model()->findByPk($id);
$this->assertTrue($candidato instanceof Candidato);
}
}
?>

View File

@ -0,0 +1,49 @@
<div class="form">
<?php $form=$this->beginWidget('CActiveForm', array(
'id'=>'usuario-form',
'enableAjaxValidation'=>false,
)); ?>
<p class="note">Fields with <span class="required">*</span> are required.</p>
<?php echo $form->errorSummary($model); ?>
<div class="row">
<?php echo $form->labelEx($model,'email'); ?>
<?php echo $form->textField($model,'email',array('size'=>60,'maxlength'=>255)); ?>
<?php echo $form->error($model,'email'); ?>
</div>
<div class="row">
<?php echo $form->labelEx($model,'name'); ?>
<?php echo $form->textField($model,'name',array('size'=>60,'maxlength'=>255)); ?>
<?php echo $form->error($model,'name'); ?>
</div>
<div class="row">
<?php echo $form->labelEx($model,'username'); ?>
<?php echo $form->textField($model,'username',array('size'=>60,'maxlength'=>255)); ?>
<?php echo $form->error($model,'username'); ?>
</div>
<div class="row">
<?php echo $form->labelEx($model,'password'); ?>
<?php echo $form->passwordField($model,'password',array('size'=>60,'maxlength'=>255)); ?>
<?php echo $form->error($model,'password'); ?>
</div>
<div class="row">
<?php echo $form->labelEx($model,'password_repeat'); ?>
<?php echo $form->passwordField($model,'password_repeat',array('size'=>60,'maxlength'=>255)); ?>
<?php echo $form->error($model,'password_repeat'); ?>
</div>
<div class="row buttons">
<?php echo CHtml::submitButton($model->isNewRecord ? 'Create' : 'Save'); ?>
</div>
<?php $this->endWidget(); ?>
</div><!-- form -->

View File

@ -0,0 +1,39 @@
<div class="wide form">
<?php $form=$this->beginWidget('CActiveForm', array(
'action'=>Yii::app()->createUrl($this->route),
'method'=>'get',
)); ?>
<div class="row">
<?php echo $form->label($model,'id'); ?>
<?php echo $form->textField($model,'id'); ?>
</div>
<div class="row">
<?php echo $form->label($model,'email'); ?>
<?php echo $form->textField($model,'email',array('size'=>60,'maxlength'=>255)); ?>
</div>
<div class="row">
<?php echo $form->label($model,'name'); ?>
<?php echo $form->textField($model,'name',array('size'=>60,'maxlength'=>255)); ?>
</div>
<div class="row">
<?php echo $form->label($model,'username'); ?>
<?php echo $form->textField($model,'username',array('size'=>60,'maxlength'=>255)); ?>
</div>
<div class="row">
<?php echo $form->label($model,'last_login_time'); ?>
<?php echo $form->textField($model,'last_login_time'); ?>
</div>
<div class="row buttons">
<?php echo CHtml::submitButton('Search'); ?>
</div>
<?php $this->endWidget(); ?>
</div><!-- search-form -->

View File

@ -0,0 +1,28 @@
<div class="view">
<b><?php echo CHtml::encode($data->getAttributeLabel('id')); ?>:</b>
<?php echo CHtml::link(CHtml::encode($data->id), array('view', 'id'=>$data->id)); ?>
<br />
<b><?php echo CHtml::encode($data->getAttributeLabel('email')); ?>:</b>
<?php echo CHtml::encode($data->email); ?>
<br />
<b><?php echo CHtml::encode($data->getAttributeLabel('name')); ?>:</b>
<?php echo CHtml::encode($data->name); ?>
<br />
<b><?php echo CHtml::encode($data->getAttributeLabel('username')); ?>:</b>
<?php echo CHtml::encode($data->username); ?>
<br />
<b><?php echo CHtml::encode($data->getAttributeLabel('password')); ?>:</b>
<?php echo CHtml::encode($data->password); ?>
<br />
<b><?php echo CHtml::encode($data->getAttributeLabel('last_login_time')); ?>:</b>
<?php echo CHtml::encode($data->last_login_time); ?>
<br />
</div>

View File

@ -0,0 +1,55 @@
<?php
$this->breadcrumbs=array(
'Usuarios'=>array('index'),
'Manage',
);
$this->menu=array(
array('label'=>'List Usuario', 'url'=>array('index')),
array('label'=>'Create Usuario', 'url'=>array('create')),
);
Yii::app()->clientScript->registerScript('search', "
$('.search-button').click(function(){
$('.search-form').toggle();
return false;
});
$('.search-form form').submit(function(){
$.fn.yiiGridView.update('usuario-grid', {
data: $(this).serialize()
});
return false;
});
");
?>
<h1>Manage Usuarios</h1>
<p>
You may optionally enter a comparison operator (<b>&lt;</b>, <b>&lt;=</b>, <b>&gt;</b>, <b>&gt;=</b>, <b>&lt;&gt;</b>
or <b>=</b>) at the beginning of each of your search values to specify how the comparison should be done.
</p>
<?php echo CHtml::link('Advanced Search','#',array('class'=>'search-button')); ?>
<div class="search-form" style="display:none">
<?php $this->renderPartial('_search',array(
'model'=>$model,
)); ?>
</div><!-- search-form -->
<?php $this->widget('zii.widgets.grid.CGridView', array(
'id'=>'usuario-grid',
'dataProvider'=>$model->search(),
'filter'=>$model,
'columns'=>array(
'id',
'email',
'name',
'username',
'password',
'last_login_time',
array(
'class'=>'CButtonColumn',
),
),
)); ?>

View File

@ -0,0 +1,15 @@
<?php
$this->breadcrumbs=array(
'Usuarios'=>array('index'),
'Create',
);
$this->menu=array(
array('label'=>'List Usuario', 'url'=>array('index')),
array('label'=>'Manage Usuario', 'url'=>array('admin')),
);
?>
<h1>Create Usuario</h1>
<?php echo $this->renderPartial('_form', array('model'=>$model)); ?>

View File

@ -0,0 +1,17 @@
<?php
$this->breadcrumbs=array(
'Usuarios',
);
$this->menu=array(
array('label'=>'Create Usuario', 'url'=>array('create')),
array('label'=>'Manage Usuario', 'url'=>array('admin')),
);
?>
<h1>Usuarios</h1>
<?php $this->widget('zii.widgets.CListView', array(
'dataProvider'=>$dataProvider,
'itemView'=>'_view',
)); ?>

View File

@ -0,0 +1,18 @@
<?php
$this->breadcrumbs=array(
'Usuarios'=>array('index'),
$model->name=>array('view','id'=>$model->id),
'Update',
);
$this->menu=array(
array('label'=>'List Usuario', 'url'=>array('index')),
array('label'=>'Create Usuario', 'url'=>array('create')),
array('label'=>'View Usuario', 'url'=>array('view', 'id'=>$model->id)),
array('label'=>'Manage Usuario', 'url'=>array('admin')),
);
?>
<h1>Update Usuario <?php echo $model->id; ?></h1>
<?php echo $this->renderPartial('_form', array('model'=>$model)); ?>

View File

@ -0,0 +1,28 @@
<?php
$this->breadcrumbs=array(
'Usuarios'=>array('index'),
$model->name,
);
$this->menu=array(
array('label'=>'List Usuario', 'url'=>array('index')),
array('label'=>'Create Usuario', 'url'=>array('create')),
array('label'=>'Update Usuario', 'url'=>array('update', 'id'=>$model->id)),
array('label'=>'Delete Usuario', 'url'=>'#', 'linkOptions'=>array('submit'=>array('delete','id'=>$model->id),'confirm'=>'Are you sure you want to delete this item?')),
array('label'=>'Manage Usuario', 'url'=>array('admin')),
);
?>
<h1>View Usuario #<?php echo $model->id; ?></h1>
<?php $this->widget('zii.widgets.CDetailView', array(
'data'=>$model,
'attributes'=>array(
'id',
'email',
'name',
'username',
'password',
'last_login_time',
),
)); ?>