The following Criteria works fine:
$criteria = new CDbCriteria(array(
'condition' => 'Id_menu = 1 ',
'select' => 'name',
'limit' => 5,
));
$dp1 = new CActiveDataProvider('post', array(
'criteria' => $criteria
));
However specifying Criteria directly on a model does not - it has no effect:
$criteria = new CDbCriteria(array(
'condition' => 'Id_menu = 1 ',
'select' => 'name',
'limit' => 5,
));
$dp1 = new CActiveDataProvider(Mdlfood::model()->find($criteria),array(),));
The following also does not work:
$criteria = new CDbCriteria(array(
'condition' => 'Id_menu = 1 ',
'select' => 'name',
'limit' => 5,
));
$model1 = new Mdlfood;
$model1->findAll($criteria);
$dp1 = new CActiveDataProvider($model1,array(),));
Can anyone explain why I cannot declare this configuration directly?
Added mdlfood
class Mdlfood extends CActiveRecord{
public function tableName()
{
return 'tblfood';
}
public function rules()
{
return array(
array('name, Url_picture, Price, Aboute, Id_foodType, Id_menu', 'required'),
array('name', 'length', 'max'=>100),
array('Url_picture, Aboute', 'length', 'max'=>2048),
array('Price, Id_foodType, Id_menu', 'length', 'max'=>20),
array('Id, name, Url_picture, Price, Aboute, Id_foodType, Id_menu', 'safe', 'on'=>'search'),
);
}
public function relations()
{
return array(
'idMenu' => array(self::BELONGS_TO, 'Tblrestmenu', 'Id_menu'),
'idFoodType' => array(self::BELONGS_TO, 'Tblfoodtype', 'Id_foodType'),
);
}
public function attributeLabels()
{
return array(
'Id' => 'ID',
'name' => 'Name',
'Url_picture' => 'Url Picture',
'Price' => 'Price',
'Aboute' => 'Aboute',
'Id_foodType' => 'Id Food Type',
'Id_menu' => 'Id Menu',
);
}
public function search()
{
// #todo Please modify the following code to remove attributes that should not be searched.
$criteria=new CDbCriteria;
$criteria->compare('Id',$this->Id,true);
$criteria->compare('name',$this->name,true);
$criteria->compare('Url_picture',$this->Url_picture,true);
$criteria->compare('Price',$this->Price,true);
$criteria->compare('Aboute',$this->Aboute,true);
$criteria->compare('Id_foodType',$this->Id_foodType,true);
$criteria->compare('Id_menu',$this->Id_menu,true);
return new CActiveDataProvider($this, array(
'criteria'=>$criteria,
));
}
public static function model($className=__CLASS__)
{
return parent::model($className);
}
}
But, I think this is not related to Model, because this Criteria work properly in the ActiveDataProvider.
Please try like this,
extra closing brackets, find()-> not in proper format
$criteria=new CDbCriteria(array(
'condition'=>'Id_menu = 1 ',
'select'=>'name',
'limit'=>5,
));
$dp1 = new CActiveDataProvider(Mdlfood::model()->find($criteria),array()); // extra closing brackets
Second way,
$criteria=new CDbCriteria(array(
'condition'=>'Id_menu = 1 ',
'select'=>'name',
'limit'=>5,
));
$model1 = new Mdlfood;
$model1->findAll($criteria);
$dp1 = new CActiveDataProvider($model1,array());
Related
I have 2 model :
$model = new ProfileInformation('internetConection');
$modeliner = new ProfileInformation('inerConection');
I show those in 2 CGridView in yii how can show in a CGridView
Model:
public function internetConection() {
// #todo Please modify the following code to remove attributes that should not be searched.
$criteria = new CDbcriteria();
$criteria->with = array('user');
$criteria->condition = 'serviceId=:serviceId';
$criteria->params = array(':serviceId' => '1');
$criteria->group = 't.user_Id';
$criteria->select = array('count(distinct psh_profile_information_services.profileInformationId) AS internetConectionCount');
$criteria->join = 'left join psh_profile_information_services on t.id=psh_profile_information_services.profileInformationId';
$criteria->order = 't.id';
$criteria->compare('user_Id', $this->user_Id);
$criteria->compare('isService', $this->isService, true);
return new CActiveDataProvider($this, array(
'criteria' => $criteria,
));
}
public function inerConection() {
// #todo Please modify the following code to remove attributes that should not be searched.
$criteria = new CDbcriteria();
$criteria->with = array('user');
$criteria->addInCondition('serviceId', array(2, 3, 4, 5));
$criteria->group = 't.user_Id';
$criteria->select = array('count(distinct psh_profile_information_services.profileInformationId) AS inerConectionCount');
$criteria->join = 'left join psh_profile_information_services on t.id=psh_profile_information_services.profileInformationId';
$criteria->order = 't.id';
$criteria->compare('user_Id', $this->user_Id);
$criteria->compare('isService', $this->isService, true);
return new CActiveDataProvider($this, array(
'criteria' => $criteria,
));
}
I am using 2 CgridView now , but if i can show in a table it is very good.
eache result search have a new field : inerConectionCount and internetConectionCount.
table for internetConectionCount
table for inernetConectionCount
I want it:
$this->widget('zii.widgets.grid.CGridView', array(
'id' => 'profile-information-grid1',
'dataProvider' => $dataprovider
'columns' => array(
array(
'header' => '',
'value' => '$this->grid->dataProvider->pagination->offset + $row+1', // row is zero based
),
array(
'name' => 'ProfileInformation.user.organization',
'value' => 'CHtml::encode($data->user->organization)',
),
array(
'name' => 'ProfileInformation.user.scope',
'value' => 'CHtml::encode($data->user->scope->name)',
'filter' => Scope::model()->options,
),
array(
'name' => 'id',
'value' => 'CHtml::encode($data->id)',
),
'inerConectionCount',
),
));
You can combine data from two providers, but you have to disable pagination or it will limit to 10 record in each providers
$model = new ProfileInformation('internetConection');
$modeliner = new ProfileInformation('inerConection');
$data = CMap::mergeArray( // combine two data
$model->search()->getData(),
$modeliner ->search()->getData()
);
$provider = new CArrayDataProvider( $data ); // use CArrayDataProvider instead of CActiveDataProvider
I have three rows in my yii CGridview and having two type of user logins.I have to hide one of the three rows depending on the type of user.Please help.
in your model add public static method
for example:
class Post extends CActiveRecord {
public function tableName() {
return 'posts';
}
public function rules() {
return array();
}
public function attributeLabels() {
return array();
}
...
public static function rulesUser() {
if ( Yii::app()->user->id = 1 ) {
return True;
} else {
return False;
}
}
add in your gridview for row:
$this->widget('zii.widgets.grid.CGridView',
array(
'id' => 'posts-grid',
'dataProvider' => $model->search(),
'filter' => $model,
'emptyText' => '',
'columns' => array(
'id',
'title',
'post',
'date_create',
array(
'name' => 'status',
'visible' => Posts::rulesUser(),
)
array(
'class' => 'CButtonColumn',
),
),
)
);
Use the Conditional statements like this:
public function newsearch()
{
$id= Yii::app()->user->id;
if($id = Your conditon){
$criteria=new CDbCriteria;
$criteria->compare('id',$this->id);
Your Criteria to display
} else {
$criteria=new CDbCriteria;
$criteria->compare('id',$this->id);
Your Criteria to display
}
return new CActiveDataProvider($this, array(
'criteria'=>$criteria,
));
}
And Call this dataprovider in your GridView data provider.
or add in model
public $visible = True;
in you search add if or switch
public function search()
{
$criteria = new CDbCriteria;
...
if (any if){
$this->visible = 1;
}
return new CActiveDataProvider($this, array(
'criteria' => $criteria,
));
}
in your gridview
...
array(
'name' => 'value',
'visible'=>$model->visible,
)
...
I have solved the task by conditioning the CDbCriteria as follows,
if(!Yii::app()->session["admin"])
{
$criteria->condition='t.unique_id!="i-8874c6e3"';
}
Thanks all.
I'm aware that similar questions have been asked, sorry, but I can't for the life of me see what I'm doing wrong. Any help would be greatly appreciated. All I want to do is to add an extra column to a CGridView that displays a total of two values in the database.
These are the steps I've taken:
Database
User(forename, surname, part1, part2)
class User extends Controller:
protected function getTotal($data,$row,$dataColumn){
return $data->getAttribute('part1')+$data->getAttribute('part2');
}
public function actionIndex(){
$dataProvider=new CActiveDataProvider('User');
$this->render('index',array(
'dataProvider'=>$dataProvider,
));
}
class Stadium extends CActiveRecord:
public function rules(){
return array(
array('forename, surname', 'required'),
array('forename', 'surname', 'max'=>50),
array('part1, part2', 'numerical', 'integerOnly'=>true),
array('forename, surname, part1, part2, total', 'safe', 'on'=>'search'),
);
}
public function attributeLabels()
{
return array(
'forename' => 'forename',
'surname' => 'surname',
'part1' => 'part1',
'part2' => 'part2',
'total' => array(
'asc'=>'part1 + part2',
'desc'=>'part1 + part2 desc',
),
);
}
public function search(){
$criteria=new CDbCriteria;
$criteria->compare('forename',$this->forename,true);
$criteria->compare('surname',$this->surname,true);
$criteria->compare('part1',$this->part1);
$criteria->compare('part2',$this->part2);
$criteria->compare('total',$this->part1 + $this->part2,true);
$sort = new CSort();
$sort->attributes = array(
'total'=>array(
'asc'=>'part1 + part2 ASC',
'desc'=>'part1 + part2 DESC',
),
'*',
);
return new CActiveDataProvider(User', array(
'criteria'=>$criteria,
'sort'=>$sort,
));
}
}
view/User/index.php
<?php $this->widget('zii.widgets.grid.CGridView', array(
'itemsCssClass'=>'table table-hover',
'dataProvider'=>$dataProvider,
'template'=>"{items}",
'columns'=>array(
array('name'=>'forename', 'header'=>'Forename'),
array('name'=>'surname', 'header'=>'Surname'),
array('name'=>'total', 'header'=>'Total', 'value'=>array($this, 'getTotal')),
),
)); ?>
<?php $this->endWidget();?>
Thanks a lot for any advice.
Solution:
Ok here is what you need to do:
class Stadium extends CActiveRecord:
public $total; //add this line
//your rules should be fine
//don't know if you need the asc and desc on attribute labels i just have one
'total' => 'Total',
$criteria->compare('total',$this->total); //change this line
//i didn't use a Csort you might be able to but this is they way i did it
return new CActiveDataProvider(User', array(
'criteria'=>$criteria,
'sort'=> array(
'attributes' => array(
'total'=>array(
'asc'=>'(part1 + part2) ASC',
'desc'=>'(part1 + part2) DESC',
),
'*',
),
),
));
//add this inside your model also
public function afterFind() {
parent::afterFind();
$this->total = $this->part1+ $this->part2;
return;
}
Everything else in your model is fine. Then on your CGridView just change the one line:
array('name'=>'total', 'header'=>'Total'), //don't need to set value it is part of the model like other columns now
http://www.yiiframework.com/forum/index.php/topic/21114-create-now-model-variable/
Original Answer:
I believe if you are going to use a CSort object you need to add it to the CActiveDataProvider using setSort() or you don't have to create a CSort you can put it straight into DataProvider.
Option 1:
$sort = new CSort();
$sort->attributes = array(
'total'=>array(
'asc'=>'part1 + part2 ASC',
'desc'=>'part1 + part2 DESC',
),
'*',
);
$data = new CActiveDataProvider(User', array(
'criteria'=>$criteria,
));
$data->setSort($sort);
return $data;
Option 2:
return new CActiveDataProvider(User', array(
'criteria'=>$criteria,
'sort'=> array(
'attributes' => array(
'total'=>array(
'asc'=>'part1 + part2 ASC',
'desc'=>'part1 + part2 DESC',
),
'*',
),
),
));
This may help
http://www.yiiframework.com/wiki/381/cgridview-clistview-and-cactivedataprovider/#hh11
http://www.yiiframework.com/doc/api/1.1/CDataProvider#setSort-detail
Pitchinnate's answer might help you, also, I've noticed a tendency from your part that you put commas where they shouldn't be present. For example
instead of:
$sort->attributes = array(
'total'=>array(
'asc'=>'part1 + part2 ASC',
'desc'=>'part1 + part2 DESC',
),
'*',
);
you need:
$sort->attributes = array(
'total'=>array(
'asc'=>'part1 + part2 ASC',
'desc'=>'part1 + part2 DESC'
),
'*'
);
you should get rid of all the commas put after the last element.
I have a problem that i can`t get throught.
I am trying to display information from relational table like this:
$dataProvider = PartnerSite::model()->with('siteCommercials')->findAll("user_id=" . Yii::app()->user->id);
$this->render('index', array(
'dataProvider' => $dataProvider,
'allMoney' => 1
));
But in my view i am seeing that error:
Relation "siteCommercials" is not defined in active record class "PartnerSite".
But the fact is that my model have relation:
public function relations() {
return array(
'goesFromSites' => array(self::HAS_MANY, 'GoesFromSite', 'site_id'),
'user' => array(self::BELONGS_TO, 'User', 'user_id'),
'siteCommercials' => array(self::HAS_MANY, 'SiteCommercial', 'site_id'),
);
}
So my question is. Is there is something wrong? I can't get it... In only one that model is a lot of problems... BeforeSave() doesn't work and relations work not well. User relation is working just fine.
Full listing of "model":
<?php
abstract class BasePartnerSite extends GxActiveRecord {
public $siteCommercials = "oke";
public static function model($className=__CLASS__) {
return parent::model($className);
}
public function tableName() {
return '{{partner_site}}';
}
public static function label($n = 1) {
return Yii::t('app', 'PartnerSite|PartnerSites', $n);
}
public static function representingColumn() {
return 'site_name';
}
public function rules() {
return array(
array('site_name', 'required'),
array('user_id', 'numerical', 'integerOnly'=>true),
array('site_name', 'length', 'max'=>255),
array('id, site_name, user_id', 'safe', 'on'=>'search'),
);
}
public function relations() {
return array(
'goesFromSites' => array(self::HAS_MANY, 'GoesFromSite', 'site_id'),
'user' => array(self::BELONGS_TO, 'User', 'user_id'),
'siteCommercials' => array(self::HAS_MANY, 'SiteCommercial', 'site_id'),
);
}
public function pivotModels() {
return array(
);
}
public function attributeLabels() {
return array(
'id' => Yii::t('app', 'ID'),
'site_name' => Yii::t('app', 'Site Name'),
'user_id' => null,
'goesFromSites' => null,
'user' => null,
'siteCommercials' => null,
);
}
public function search() {
$criteria = new CDbCriteria;
$criteria->compare('id', $this->id);
$criteria->compare('site_name', $this->site_name, true);
$criteria->compare('user_id', $this->user_id);
return new CActiveDataProvider($this, array(
'criteria' => $criteria,
));
}
}
Your class is BasePartnerSite. In this class you define relation siteCommercials.
Your error message: "Relation "siteCommercials" is not defined in active record class "PartnerSite".
So then shouldn't your code be?
$dataProvider = BasePartnerSite::model()->with('siteCommercials')->findAll("user_id=" . Yii::app()->user->id);
$model=new Event('create');
$model->attributes=$_POST['Event'];
if($model->save()){
$pkg = new Package();
$pkg->attributes=$_POST['Package'];
$pkg->event_id = $model->id;
$pkg->save();
}
The Event model gets saved correctly with all the POST variables for Event, while the Package only has the event_id set, but no attributes are set (they are all NULL). What am I doing wrong?
NB: The Event object has been programmed by my predecessor, the Package object is a new addition I did.
EDIT: the whole Package class
class Package extends CActiveRecord
{
public static function model($className=__CLASS__)
{
return parent::model($className);
}
public function tableName()
{
return 'tbl_package';
}
public function rules()
{
// NOTE: you should only define rules for those attributes that
// will receive user inputs.
return array(
// The following rule is used by search().
// Please remove those attributes that should not be searched.
array('', 'safe', 'on'=>'search'),
array('', 'numerical'),
);
}public function relations()
{
// NOTE: you may need to adjust the relation name and the related
// class name for the relations automatically generated below.
return array(
'event' => array(self::BELONGS_TO, 'Event', 'id')
);
}public function attributeLabels()
{
return array(
'event_id' => 'Event ID',
'package_name' => 'Package name',
'event_banner' => 'Event Banner',
'ad_placement' => 'Ad Placement in Event Program',
'logo_on_step' => 'Logo on Step & Repeat',
'use_evt_pics' => 'Usage of Event Pictures',
'exhibition' => 'Exhibition Booth/Space',
'inc_press' => 'Inclusion in Press',
'print_ads' => 'Insertion in Print Ads',
'online_ads' => 'Insertion in Online Ads',
'attendee_bags' => 'Attendee Bags',
'charging_st' => 'Charging Stations',
'cups' => 'Coffee/Water Cups',
'distr_items' => 'Distributable Items',
'lanyards' => 'Lanyards',
'napkins' => 'Napkins',
'notebooks' => 'Notebooks',
'pens' => 'Pens',
'seat_covers' => 'Seat Covers',
'snack_pack' => 'Snack Packaging',
'water_bottles' => 'Water Bottles'
);
} public function search()
{
// Warning: Please modify the following code to remove attributes that
// should not be searched.
$criteria=new CDbCriteria;
$criteria->compare('event_banner',$this->event_banner);
$criteria->compare('package_name',$this->package_name);
$criteria->compare('ad_placement',$this->ad_placement);
$criteria->compare('logo_on_step',$this->logo_on_step);
$criteria->compare('use_evt_pics',$this->use_evt_pics);
$criteria->compare('exhibition',$this->exhibition);
$criteria->compare('inc_press',$this->inc_press);
$criteria->compare('print_ads',$this->print_ads);
$criteria->compare('online_ads',$this->online_ads);
$criteria->compare('attendee_bags',$this->attendee_bags);
$criteria->compare('charging_st',$this->charging_st);
$criteria->compare('cups',$this->cups);
$criteria->compare('distr_items',$this->distr_items);
$criteria->compare('lanyards',$this->lanyards);
$criteria->compare('napkins',$this->napkins);
$criteria->compare('notebooks',$this->notebooks);
$criteria->compare('pens',$this->pens);
$criteria->compare('seat_covers',$this->seat_covers);
$criteria->compare('snack_pack',$this->snack_pack);
$criteria->compare('water_bottles',$this->water_bottles);
return new CActiveDataProvider('SponsorshipPackage', array(
'criteria'=>$criteria,
));
}
}
If you want to set attributes through:
$pkg->attributes=$_POST['Package'];
then you have to set rules for any attribute that can be set this way.
You need something like this:
public function rules()
{
// NOTE: you should only define rules for those attributes that
// will receive user inputs.
return array(
array('package_name', 'required'),
array('package_name', 'length', 'max' => 255),
// or
array('package_name', 'length', 'max' => 255, 'on' => 'insert'),
// at least (when no validation is required):
array('package_name', 'safe'),
// ...
// and so on..
);
}
you need rule for any attribute that you want to set this way.
if there is no rule set for attribute you'll be able to set its value only through $pkg->attribute_name = $value;
rule like array('', 'safe', 'on'=>'search'), or array('', 'numerical'), does nothing (cause attributes list is empty).
read more about validation here
class Package extends CActiveRecord
{
public static function model($className=__CLASS__)
{
return parent::model($className);
}
public function tableName()
{
return 'tbl_package';
}
public function rules()
{
// NOTE: you should only define rules for those attributes that
// will receive user inputs.
return array(
// The following rule is used by search().
// Please remove those attributes that should not be searched.
array('ad_placement, logo_on_step, ...', 'safe', 'on'=>'search'), //note put here all attrs name that you feel those attrs needs to be assigned from POST like: `$pkg->attributes=$_POST['Package'];`
array('event_id', 'numerical'),
);
}public function relations()
{
// NOTE: you may need to adjust the relation name and the related
// class name for the relations automatically generated below.
return array(
'event' => array(self::BELONGS_TO, 'Event', 'id')
);
}public function attributeLabels()
{
return array(
'event_id' => 'Event ID',
'package_name' => 'Package name',
'event_banner' => 'Event Banner',
'ad_placement' => 'Ad Placement in Event Program',
'logo_on_step' => 'Logo on Step & Repeat',
'use_evt_pics' => 'Usage of Event Pictures',
'exhibition' => 'Exhibition Booth/Space',
'inc_press' => 'Inclusion in Press',
'print_ads' => 'Insertion in Print Ads',
'online_ads' => 'Insertion in Online Ads',
'attendee_bags' => 'Attendee Bags',
'charging_st' => 'Charging Stations',
'cups' => 'Coffee/Water Cups',
'distr_items' => 'Distributable Items',
'lanyards' => 'Lanyards',
'napkins' => 'Napkins',
'notebooks' => 'Notebooks',
'pens' => 'Pens',
'seat_covers' => 'Seat Covers',
'snack_pack' => 'Snack Packaging',
'water_bottles' => 'Water Bottles'
);
}
....
}
If it does not work, then you may try, htere is validate() method before save():
$model=new Event('create');
$model->attributes=$_POST['Event'];
if($model->validate()){
$model->save();
}
else{
echo CHtml::errorSummary($model);
}
This will tell what is error.
Never save direct, validate it before save.