I coded member staff, in a way the members staffs will be shown under a company’s detail page.
now, whenever I click the company id from the index file, I get redirected to the company’s full view detail page, and underneath it is a list of the member staff with pagination.
I did the same coding with the Company Controller by adding a filter so a Member can only
create a company when he is logged in and view his own companies,
the problem now is, a different member logged in, can view the companies of other members what’s the best approach with this?,
here’s my filter code within the Company controller
public function filters()
{
return array(
'accessControl', // perform access control for CRUD operations
'memberContext + create',
);
}
public function filterMemberContext($filterChain)
{
$member_id = null;
if(isset($_GET['mid']))
$member_id = $_GET['mid'];
else
if(isset($_POST['mid']))
$member_id = $_POST['mid'];
$this->loadMember($member_id);
$filterChain->run();
}
I am usually doing this kind of check in the model.
I write an afterfind function like:
public function afterFind()
{
if ($this->owner!= Yii::app()->user->userId)
throw new Exception('you are not authorized to see this company');
}
This will protect you to unauthorized access to the model itself, so you cannot forget some check in any action you create or you will create in future.
I like this approach because is "putting business logic in models".
are you trying this in your company model? because im using this code and its working fine for me…
public function search()
{
// Warning: Please modify the following code to remove attributes that
// should not be searched.
$criteria=new CDbCriteria;
$criteria->compare('t.membershipid=',Yii::app()->user->id,true);
return new CActiveDataProvider(get_class($this), array(
There can be many possibily: maybe the Yii::app()->user->id is not correct, check it.
Another option is that you are querying all the companyies, including the companies that a user is not allowed to see. In that case the exception is the expected behaviour, you have to query only the right models.
In the bottom line of the code there is an error, the = is not needed in compare.
Check the query that yii generates, for be sure that you have configured all criteria in a correct way.
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.
*/
private $_id;
const ERROR_EMAIL_INACTIVE = 3;
public function authenticate()
{
$record = Wsmembers::model()->findByAttributes(array('WSLoginName' => $this->username));
$email = Wsmembers::model()->findByAttributes(array('WSEmailConfirmed' => 0));
if($record === null)
$this->errorCode = self::ERROR_USERNAME_INVALID;
else if($record->WSLoginPassword !== sha1($this->password))
$this->errorCode = self::ERROR_PASSWORD_INVALID;
else if($email)
$this->errorCode = self::ERROR_EMAIL_INACTIVE;
else
{
$this->_id = $record->MemberShipID;
$this->setState('name', $record->WSLoginName);
$this->errorCode = self::ERROR_NONE;
}
return !$this->errorCode;
}
public function getId()
{
return $this->_id;
}
}
This one is responsible for displaying the companies for an existing User
I applied what I learned from the yii book
<?php
class WsmembersdetailsController extends Controller
{
private $_member = null;
/**
* @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
'memberContext + create',
);
}
/**
* 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)
{
$staffDataProvider = new CActiveDataProvider('Wsmembersstaff', array(
'criteria' => array(
'condition' => 'CompanyID=:CompanyID',
'params' =>array(':CompanyID'=>$this->loadModel($id)->CompanyID),
),
'pagination' => array(
'pageSize' => 1,
),
));
$this->render('view',array(
'model'=>$this->loadModel($id),
'staffDataProvider'=>$staffDataProvider,
));
}
/**
* Creates a new model.
* If creation is successful, the browser will be redirected to the 'view' page.
*/
public function actionCreate()
{
$model=new Wsmembersdetails;
$model->MemberShipID = $this->_member->MemberShipID;
// Uncomment the following line if AJAX validation is needed
// $this->performAjaxValidation($model);
if(isset($_POST['Wsmembersdetails']))
{
$model->attributes=$_POST['Wsmembersdetails'];
if($model->save())
$this->redirect(array('view','id'=>$model->CompanyID));
}
$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['Wsmembersdetails']))
{
$model->attributes=$_POST['Wsmembersdetails'];
if($model->save())
$this->redirect(array('view','id'=>$model->CompanyID));
}
$this->render('update',array(
'model'=>$model,
));
}
/**
* Deletes a particular model.
* If deletion is successful, the browser will be redirected to the 'index' 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('Wsmembersdetails');
$this->render('index',array(
'dataProvider'=>$dataProvider,
));
}
/**
* Manages all models.
*/
public function actionAdmin()
{
$model=new Wsmembersdetails('search');
$model->unsetAttributes(); // clear any default values
if(isset($_GET['Wsmembersdetails']))
$model->attributes=$_GET['Wsmembersdetails'];
$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=Wsmembersdetails::model()->findByPk((int)$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']==='wsmembersdetails-form')
{
echo CActiveForm::validate($model);
Yii::app()->end();
}
}
protected function loadMember($member_id)
{
if($this->_member === null)
{
$this->_member = Wsmembers::model()->findByPk($member_id);
if($this->_member === null)
{
throw new CHttpException(404, 'The requested project does not exist.');
}
}
return $this->_member;
}
public function filterMemberContext($filterChain)
{
$member_id = null;
if(isset($_GET['mid']))
$member_id = $_GET['mid'];
else
if(isset($_POST['mid']))
$member_id = $_POST['mid'];
$this->loadMember($member_id);
$filterChain->run();
}
}