I want to make a custom widget like one of the examples that yii brings (blog), and the custom widget i want to make is the one called "RecentPosts", but for my page i'm going to call it "RecentTasks", so i just want to get the firsts 4 tasks on my database SQLite(almos like "recentPost" does).
in my column2:
<?php /* #var $this Controller */ ?>
<?php $this->beginContent('//layouts/main'); ?>
<div class="col-xs-12 col-sm-9">
<div id="content">
<?php echo $content; ?>
</div><!-- content -->
</div>
<div id="sidebar" class="col-xs-6 col-sm-3 sidebar-offcanvas" role="navigation">
<div class="list-group">
<?php
// $this->beginWidget('zii.widgets.CPortlet', array(
// 'title'=>'Operations',
// ));
$this->widget('zii.widgets.CMenu', array(
'items'=>$this->menu,
'htmlOptions'=>array('class'=>'nav nav-pills nav-stacked'),
));
// $this->endWidget();
?>
<?php
$this->widget('recentTasks', array(
'maxTasks'=>10
));
?>
</div>
</div>
<?php $this->endContent(); ?>
in my custom widget inside components:
<?php
Yii::import('zii.widgets.CPortlet');
class RecentTasks extends CPortlet
{
public $title = 'Recent Tasks';
public $maxTasks = 10;
public function getRecentTasks()
{
return Task::model()->findRecentTasks($this->maxTasks);
}
protected function renderContent()
{
$this->render('recentTasks');
}
}
my model:
<?php
class Task extends CActiveRecord
{
/**
* #return string the associated database table name
*/
public function tableName()
{
return 'task';
}
public function rules()
{
// NOTE: you should only define rules for those attributes that
// will receive user inputs.
return array(
array('Name, Status, Project_id, User_id', 'required'),
array('Status, Project_id, User_id', 'numerical', 'integerOnly'=>true),
array('Name, Create_time, Update_time, Assigned', 'length', 'max'=>45),
array('Description, Tags', 'safe'),
// The following rule is used by search().
// #todo Please remove those attributes that should not be searched.
array('id, Name, Description, Status, Create_time, Update_time, Tags, Project_id, User_id, Assigned', 'safe', 'on'=>'search'),
);
}
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(
'comments' => array(self::HAS_MANY, 'Comment', 'Task_id'),
'project' => array(self::BELONGS_TO, 'Project', 'Project_id'),
'user' => array(self::BELONGS_TO, 'User', 'User_id'),
);
}
public function attributeLabels()
{
return array(
'id' => 'ID',
'Name' => 'Name',
'Description' => 'Description',
'Status' => 'Status',
'Create_time' => 'Create Time',
'Update_time' => 'Update Time',
'Tags' => 'Tags',
'Project_id' => 'Project',
'User_id' => 'User',
'Assigned' => 'Assigned',
);
}
public function findRecentTasks($limit=10)
{
$this->findAll();
}
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);
$criteria->compare('Name',$this->Name,true);
$criteria->compare('Description',$this->Description,true);
$criteria->compare('Status',$this->Status);
$criteria->compare('Create_time',$this->Create_time,true);
$criteria->compare('Update_time',$this->Update_time,true);
$criteria->compare('Tags',$this->Tags,true);
$criteria->compare('Project_id',$this->Project_id);
$criteria->compare('User_id',$this->User_id);
$criteria->compare('Assigned',$this->Assigned,true);
return new CActiveDataProvider($this, array(
'criteria'=>$criteria,
));
}
public static function model($className=__CLASS__)
{
return parent::model($className);
}
}
in the view of the widget im just making var_dump($this->getRecentTasks());
i haven't figure out the problem but for now its just returning NULL. I followed almost the exact same steps made on the example page in yii
Try this:
// location: /protected/components/RecentTasks.php
class RecentTasks extends CWidget
{
public $title = 'Recent Tasks';
public $maxTasks = 10;
/**
* Is called when $this->beginWidget() is called
*/
public function init()
{
}
/**
* Is called when $this->endWidget() is called
*/
public function run()
{
// render /protected/components/views/recentTasks.php
$this->render('recentTasks', array(
'models'=>$this->getRecentTasks($this->maxTasks)
));
}
public function getRecentTasks()
{
return Task::model()->findRecentTasks($this->maxTasks);
}
}
Call the widget like so in your view or layout file (with a capital):
$this->widget('RecentTasks', array(
'maxTasks'=>10
));
Then you can use $models in the view to show the tasks.
Also see: http://www.yiiframework.com/doc/guide/1.1/en/basics.view#widget
EDIT:
Seems the problem is in your findRecentTasks() method, add return before the findAll(). I also added the code to apply the limit and for conditions may you need that in the future.
public function findRecentTasks($limit=10)
{
return $this->findAll(array(
// 'condition'=>'id = :id',
// 'params' => array('id'=>$id),
'limit'=>$limit
));
}
Related
I am using Microsoft SQL Server as my database and yii1.1 framework
$model = new Test();
$model->name = "test";
$model->save();
echo $model->id;
I can't get the id this way shown above the code. It doesn't return anything but the data is being saved to the database.
Here is my test class which I have generated through gii
<?php
class Test extends CActiveRecord
{
public static function model($className=__CLASS__)
{
return parent::model($className);
}
public function tableName()
{
return 'test';
}
public function rules()
{
return array(
array('name', 'length', 'max'=>10),
array('id, name', 'safe', 'on'=>'search'),
);
}
public function relations()
{
return array(
);
}
public function attributeLabels()
{
return array(
'id' => 'ID',
'name' => 'Name',
);
}
public function search()
{
$criteria=new CDbCriteria;
$criteria->compare('id',$this->id);
$criteria->compare('name',$this->name,true);
return new CActiveDataProvider($this, array(
'criteria'=>$criteria,
));
}
}
i have problems with duplication of pk, and only users model is saved then the rest will 0 value,
need help guys. thanks in advance
Model: Student [edited]
public function rules()
{
// NOTE: you should only define rules for those attributes that
// will receive user inputs.
return array(
array('studentid', 'required'),
array('studentid', 'unique'),
array('studentid, year, cellphonenumber', 'numerical', 'integerOnly'=>true),
array('lastname, firstname, middlename, course, email', 'length', 'max'=>32),
// The following rule is used by search().
// #todo Please remove those attributes that should not be searched.
array('studentid, lastname, firstname, middlename, course, year, cellphonenumber, email', 'safe', 'on'=>'search'),
);
}
/**
* #return array relational rules.
*/
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(
);
}
/**
* #return array customized attribute labels (name=>label)
*/
public function attributeLabels()
{
return array(
'studentid' => 'Studentid',
'lastname' => 'Lastname',
'firstname' => 'Firstname',
'middlename' => 'Middlename',
'course' => 'Course',
'year' => 'Year',
'cellphonenumber' => 'Cellphonenumber',
'email' => 'Email',
);
}
/**
* Retrieves a list of models based on the current search/filter conditions.
*
* Typical usecase:
* - Initialize the model fields with values from filter form.
* - Execute this method to get CActiveDataProvider instance which will filter
* models according to data in model fields.
* - Pass data provider to CGridView, CListView or any similar widget.
*
* #return CActiveDataProvider the data provider that can return the models
* based on the search/filter conditions.
*/
public function search()
{
// #todo Please modify the following code to remove attributes that should not be searched.
$criteria=new CDbCriteria;
$criteria->compare('studentid',$this->studentid);
$criteria->compare('lastname',$this->lastname,true);
$criteria->compare('firstname',$this->firstname,true);
$criteria->compare('middlename',$this->middlename,true);
$criteria->compare('course',$this->course,true);
$criteria->compare('year',$this->year);
$criteria->compare('cellphonenumber',$this->cellphonenumber);
$criteria->compare('email',$this->email,true);
return new CActiveDataProvider($this, array(
'criteria'=>$criteria,
));
}
/**
* Returns the static model of the specified AR class.
* Please note that you should have this exact method in all your CActiveRecord descendants!
* #param string $className active record class name.
* #return Student the static model class
*/
public static function model($className=__CLASS__)
{
return parent::model($className);
}
}
Controller:
public function actionCreateUsers()
{
$vm = (object) array();
$vm->Users=new Users;
$vm->Student=new Student;
$vm->Instructor=new Instructor;
$holder;
// $model=new Users;
// Uncomment the following line if AJAX validation is needed
// $this->performAjaxValidation($model);
if(isset($_POST['Users']))
{
$vm->Users->attributes=$_POST['Users'];
$vm->Users->save();
if(isset($_POST['Student']))
{
$vm->Student->attributes=$_POST['Student'];
$vm->Student->studentid = $vm->Users->username;
if($vm->Student->save())
$vm->Student->unsetAttributes();
}
if(isset($_POST['Instructor']))
{
$vm->Instructor->attributes=$_POST['Instructor'];
$vm->Instructor->instructorid = $vm->Users->username;
if($vm->Instructor->save())
$vm->Instructor->unsetAttributes();
}
else {
return false;
}
}
// echo 'saved';
// $this->redirect(array('view','id'=>$model->username));
$vm->Users->unsetAttributes();
$vm->Student->unsetAttributes();
$vm->Instructor->unsetAttributes();
$this->render('users',array(
'vm'=>$vm,
));
}
View:
Hi Please provide the code
As you said that one model is saving but others are not. This may be the issue of rules define in model.
Try to getErrors() if model doesn't save
$vm = (object) array();
$vm->Users=new Users;
$vm->Student=new Student;
$vm->Instructor=new Instructor;
$holder;
// $model=new Users;
// Uncomment the following line if AJAX validation is needed
// $this->performAjaxValidation($model);
if(isset($_POST['Users']))
{
$vm->Users->attributes=$_POST['Users'];
$vm->Users->save();
if(isset($_POST['Student']))
{
$vm->Student->attributes=$_POST['Student'];
$vm->Student->studentid = $vm->Users->username;
if($vm->Student->save())
$vm->Student->unsetAttributes();
else{
print_r($vm->Student->getErrors());die;// to get errors
}
}
if(isset($_POST['Instructor']))
{
$vm->Instructor->attributes=$_POST['Instructor'];
$vm->Instructor->instructorid = $vm->Users->username;
if($vm->Instructor->save())
$vm->Instructor->unsetAttributes();
else{
print_r($vm->Instructor->getErrors());die;// to get errors
}
}
else {
return false;
}
}
// echo 'saved';
// $this->redirect(array('view','id'=>$model->username));
$vm->Users->unsetAttributes();
$vm->Student->unsetAttributes();
$vm->Instructor->unsetAttributes();
$this->render('users',array(
'vm'=>$vm,
));
}
In order to debug, remember you can add:
if($vm->Student->save()) {
$vm->Student->unsetAttributes();
} else {
var_dump($vm->getErrors());
die;
}
Same for instructors. Hope it helps
I have model like below, where i have defined some static variables (which is not in DB table) then i am trying to fetch those variables but it returns those variables which is in DB table. I am trying to fetch both variables (static variables as well as variables which is in DB table).
Model
class Eforms extends CActiveRecord
{
public $emp_name;
public $current_status;
public $action_type;
public $action_type_extra;
public $common_value = array(
1 => 'Yes',
2 => 'No',
);
public $hr_only_value = array(
1 => 'IT',
2 => 'BOLD',
);
public static function model($className=__CLASS__)
{
return parent::model($className);
}
public function tableName()
{
return 'tbl_eforms';
}
public function rules()
{
return array(
array('form_id', 'required'),
array('form_id, user_id', 'numerical', 'integerOnly'=>true),
array('name_in_form', 'length', 'max'=>500),
array('pdf_name', 'length', 'max'=>1000),
array('emp_name, current_status, action_type, action_type_extra', 'required', 'on'=>'form1'),
array('emp_name, current_status, action_type, action_type_extra','safe'),
// The following rule is used by search().
// Please remove those attributes that should not be searched.
array('id, form_id, user_id, name_in_form, email_recipients, pdf_name, created_on', 'safe', 'on'=>'search'),
);
}
................
...............
Controller :
public function actionIndex()
{
$model=new Eforms;
var_dump($model->attributes);exit;
}
If i changes CActiveRecord with CFormModel the it returns the only static variables not the DB related one.
From yii1 doc http://www.yiiframework.com/doc/api/1.1/CActiveRecord#attributes-detail
$model->attributes
Returns all column attribute values. Note, related objects are not
returned.
So you can access to the (related/calculated) var using
$myVar = $model->emp_name;
or
$model->emp_name = 'my_emp_name_value';
I created 2 mysql views, and has generated from them 2 model.
MostPopularCoupon
class MostPopularCoupon extends CActiveRecord
{
public function tableName()
{
return 'most_popular_coupon';
}
public function rules()
{
return array(
array('coupon_id', 'required'),
array('coupon_id', 'numerical', 'integerOnly'=>true),
array('left_coupons', 'length', 'max'=>22),
array('stopped_at', 'safe'),
array('left_coupons, coupon_id, stopped_at', 'safe', 'on'=>'search'),
);
}
public function relations()
{
return array(
);
}
public function attributeLabels()
{
return array(
'left_coupons' => 'Left Coupons',
'coupon_id' => 'Coupon',
'stopped_at' => 'Stopped At',
);
}
public function search()
{
$criteria=new CDbCriteria;
$criteria->compare('left_coupons',$this->left_coupons,true);
$criteria->compare('coupon_id',$this->coupon_id);
$criteria->compare('stopped_at',$this->stopped_at,true);
return new CActiveDataProvider($this, array(
'criteria'=>$criteria,
));
}
public static function model($className=__CLASS__)
{
return parent::model($className);
}
}
MostActiveCity
class MostActiveCity extends CActiveRecord
{
public function tableName()
{
return 'most_active_city';
}
public function rules()
{
return array(
array('mines', 'length', 'max'=>21),
array('city', 'length', 'max'=>255),
array('mines, city', 'safe', 'on'=>'search'),
);
}
public function relations()
{
return array();
}
public function attributeLabels()
{
return array(
'mines' => 'Mines',
'city' => 'City',
);
}
public function search()
{
$criteria=new CDbCriteria;
$criteria->compare('mines',$this->mines,true);
$criteria->compare('city',$this->city,true);
return new CActiveDataProvider($this, array(
'criteria'=>$criteria,
));
}
public static function model($className=__CLASS__)
{
return parent::model($className);
}
}
But due to no experience, don't know how to use them correctly. I need to substitute company_id in the query to get the data of the company belongs to the current user...
Please relock at your design. You would be better off having model classes of City{} and Coupon{}, then have functions for example MostPopularCoupons inside the Coupon class. You could then call them as functions of the class. For example.
In your model
class Coupon extends CActiveRecord
{
// NOTE: This is important for your alias column.
public $couponCount;
public function tableName()
{
return 'coupon';
}
...
public function MostPopularCoupons()
{
$Criteria = new CDbCriteria();
$Criteria->select = ' count(*) as couponCount ';
$lstCoupons = Coupon::model()->findAll($Criteria);
return $lstCoupons;
}
}
Then, in your controller
$coupon_id = 10;
$model1 = Coupon::model()->findByPK((int)$coupon_id);
$lstCouponCount = Coupon::MostPopularCoupons();
I wish to list some Categories name on my layout main.php page.
Since the layout doesn't have any associated controller or model, I wish to create a static method like this on Category model:
public static function getHeaderModels()
{
// get all models here
return $models;
}
and then in the main layout
<?php
$models = Category::getHeaderModels();
foreach($models as $model)
{
// ....
}
?>
My question is a very basic one:
How can I retrieve those category names from the model ?
Here is the full model:
class Category extends CActiveRecord {
public static function model($className=__CLASS__) {
return parent::model($className);
}
public function tableName() {
return 'category';
}
public function rules() {
return array(
array('parent_id', 'numerical', 'integerOnly' => true),
array('name', 'length', 'max' => 255),
array('id, parent_id, name', 'safe', 'on' => 'search'),
);
}
public function relations() {
return array(
'users' => array(self::MANY_MANY, 'User', 'categories(category_id, user_id)'),
);
}
public function scopes()
{
return array(
'toplevel'=>array(
'condition' => 'parent_id IS NULL'
),
);
}
public function attributeLabels() {
$id = Yii::t('trans', 'ID');
$parentId = Yii::t('trans', 'Parent');
$name = Yii::t('trans', 'Name');
return array(
'id' => $id,
'parent_id' => $parentId,
'name' => $name,
);
}
public function search() {
$criteria = new CDbCriteria;
$criteria->compare('id', $this->id);
$criteria->compare('parent_id', $this->parent_id);
$criteria->compare('name', $this->name, true);
return new CActiveDataProvider(get_class($this), array(
'criteria' => $criteria,
));
}
public static function getHeaderModels() {
//what sintax should I use to retrieve the models here ?
return $models;
}
May be this answer can help you. First you must create a Widget so you can use it more effectively.
First Create a new widget. Let say the name is CategoryWidget. Put this widget under components directory protected/components.
class CategoryWidget extends CWidget {
public function run() {
$models = Category::model()->findAll();
$this->render('category', array(
'models'=>$models
));
}
}
Then create a view for this widget. The file name is category.php.
Put it under protected/components/views
category.php
<?php if($models != null): ?>
<ul>
<?php foreach($models as $model): ?>
<li><?php echo $model->name; ?></li>
<?php endforeach; ?>
</ul>
<?php endif; ?>
Then call this widget from your main layout.
main.php
// your code ...
<?php $this->widget('CategoryWidget') ?>
...
If I'm not mistaken, you can also pass any variable available in a view, on to the layout.
You just do it from the view that has your variable.
This is the catch: you need to declare the variable which will receive your value, in the controller, like this:
<?php
class MyController extends Controller
{
public $myvariable;
After this, you will assign your model or whatever to this public variable inside your view,
like this:
$this->myvariable = $modeldata;
After you have assigned your model data to controller's public attribute,
you can easily display it inside your layout e.g.
echo $this->myvariable;
Yii already does this by assigning menu items to column2 sidebar menu, from view, like this:
$this->menu=array(
array('label'=>'List Item', 'url'=>array('index')),
array('label'=>'Manage Item', 'url'=>array('admin')),
);
You can see it in all create/update views that gii crud creates.