Yii 1.1: listbehavior

Easy working with status-like attributtes of active record (represent text and html for integer values)

Let's assume you have active record with Status attribute. Status can be Created, Confirmed and Rejected. In database table you have column status_id and store ID of each status according to some map, e.g.
ID Status
0 Created
10 Confirmed
20 Rejected


There are two ways of storing text representation of statuses:
1. create additional table in database, e.g. tbl_status (id, text), create Status model and setup relation
2. store in php code as constants (and this extension should help)

If you have many statuses or they are changing frequently I suggest to use first way.
But if statuses more or less fixed and you don't want to create additional table/model you can try ListBehavior. With it you can easliy use constants (such as STATUS_CREATED etc.), show text and html representations and get array with all values (for dropdown).


Developed and tested on Yii 1.1.10


1.Copy ListBehavior.php into protected/components folder.
2.Create your class extending ListBehavior like this:

class StatusBehavior extends ListBehavior 
    const CREATED                = 1;
    const CONFIRMED              = 10;
    const CANCELLED              = 20;
    public function data()
        return array(
            self::CREATED          => array('text' => 'Created',     'color' => 'gray'),
            self::CONFIRMED        => array('text' => 'Confirmed',   'color' => 'green'),  
            self::CANCELLED        => array('text' => 'Rejected',    'color' => 'red'),  
   /* or if you need only text
    public function data()
        return array(
            self::CREATED          => 'Created',
            self::CONFIRMED        => 'Confirmed',
            self::CANCELLED        => 'Rejected',  

You can put this file to models directory as it's looks like tiny model.

3.Attach your behavior to active record (attribute parameter is requred):

class Document extends CActiveRecord
    public function behaviors()
        return array(      
           'status' => array(
                'class' => 'StatusBehavior',
                'attribute' => 'status_id',

4.That's it! Now you can use it via $model->status->text and $model->status->html.

$model = Document::model()->findByPk($pk);
echo $model->status->html;

Or in columns property of CGridView:

$this->widget('zii.widgets.grid.CGridView', array(
  'columns' = array(
       'type' => 'raw',
       'header' => 'Document Status',
       'value' => '$data->status->html',

To get array with all possible values (e.g. for dropdown in form):

$listData = Document::model()->status->getList();
echo $form->activeDropDownList($model, 'status_id', $listData);


  • you can change html representation via parameter htmlTemplate. It's default value is:
<span style="color: {color}">{text}</span>

There can be any tokens taken from array keys of data() method.

  • you can change text for not-found values via undefinedText param.
  • you can easily use constants like this way:
if($model->status_id == StatusBehavior::CREATED) {


May, 8
Redesigned and fixed #8032

April, 23
Initial release

All comments are welcome!

Total 8 comments

#12490 report it
Nur Rochim at 2013/03/23 12:21pm

Wow.... best extension! thanks :)

#8071 report it
Vitalets at 2012/05/08 11:01am

hi jmariani! It's usual CGridView.
Thank you!

#8070 report it
jmariani at 2012/05/08 10:48am
RE: redesigned and fixed


Thank you very much. I'll test the new version ASAP. Glad I helped to improve.

Question: Which grid are you using in your screenshot?


#8069 report it
Vitalets at 2012/05/08 10:41am
redesigned and fixed

I've redesigned extension according to your comment. Now text and html values are populated in getText / getHtml methods.
so usage is the same but it's far more flexible as there is no dependency from afterFind / afterSave events and it does not matter was model saved or not.
Thank you!

#8032 report it
jmariani at 2012/05/04 12:30pm
Null value returned

I think I found the problem. You're populating the values with afterFind.

But if you create a new model, save, and then try to inspect the value, if will not be populated. So I fixed it by replicating your afterFind function in an afterSave function and now it works.

Pending fix is when you create a new model and try to inspect the value with the model unsaved.

I'll check that later.


#8030 report it
jmariani at 2012/05/04 12:11pm
Null value returned


This is my behavior code:

class CfdTypeBehavior extends ListBehavior {
    const INVOICE = 0;
    const CREDIT_MEMO = 1;
    const TRANSPORT = 2;
    public function data() {
        return array(
            self::INVOICE => array('text' => 'ingreso'),
            self::CREDIT_MEMO => array('text' => 'egreso'),
            self::TRANSPORT => array('text' => 'traslado'),

This is my behaviors() function:

public function behaviors() {
        return array(
            'CTimestampBehavior' => array(
                'class' => 'zii.behaviors.CTimestampBehavior',
                'createAttribute' => 'creationDt',
                'updateAttribute' => 'updateDt',
           'voucher' => array(
                'class' => 'CfdTypeBehavior',
                'attribute' => 'voucherType',
           'status' => array(
                'class' => 'CfdStatusBehavior',
                'attribute' => 'status',

The column voucherType in the table contains a value of 0. When I do this:

echo $this->voucher->text;

I get an empty value instead of "ingreso".

Any clues?


#8014 report it
jmariani at 2012/05/03 02:15pm

I like this extension. Thank you very much!

#7876 report it
JFReyes at 2012/04/24 09:02am
Works nicely

This will save me some work as I use a few of these data structures. Thanks!

Leave a comment

Please to leave your comment.

Create extension