YiiFramework adding functions to your models
MVC has some principals to it, like the fat model principal that I’ll show in this tutorial and which is used in a lot of frameworks. I’m going to show how to add and use functions that can be added to a model.
There are a few ways to add to a models that increase code re-usability. One way is to just add methods to the models, methods which can execute complex queries and make your controller thinner.
The first example, a query that will get all products within a price range, it will need a limit and an offset for pagination, so in the Products model, the following function can be added:
1 public function findAllByPrice($min=0, $max=1000000, $offset = 0, $limit = 30) {2 $Criteria = new CDbCriteria();3 $Criteria->condition = "price >= :min AND price <=:max";4 $Criteria->limit = $limit;5 $Criteria->offset = $offset;6 $Criteria->params = array ( ':min' => $min, ':max' => $max );7 return $this->with(array('brand'))->findAll($Criteria);8 }
Now in any of the controlller files this method can be easily accessed and returns all of the ‘Product’ objects with a single line command:
1 $Products = Product::model()->findAllByPrice(100, 700, 0, 30);
Another way to do the same is to:
1 public function getProducts($category){2 return $this->findAll('categoryIdFk=:category', array(':category'=>$category));3 }
Let’s implement the first query using two named scope methods that I’ll create.
1 // Price Between - Named Scope ---------------------------------//2 public function scopePriceBetween($min, $max) {3 $Criteria = new CDbCriteria();4 $Criteria->condition = "$this->tableName().price BETWEEN :min AND :max";5 $Criteria->params = array(':min' => $min, ':max' => $max);6 $this->getDbCriteria()->mergeWith($Criteria);7 return $this;8 }
Now an additional named scope for the limit element
1 // Limit - Named Scope --------------------------------------//2 public function scopeLimit($limit = 30, $offset = 0) {3 $Criteria = new CDbCriteria();4 $Criteria->limit = $limit;5 $Criteria->offset = $offset;6 $this->getDbCriteria()->mergeWith($Criteria);7 return $this;8 }
Now we can simply use our named scopes to get our data back, and then we could continue to pile on named scopes to return our data.
1 $Products = Product::model()->scopePriceBetween(0, 5000) ->scopeLimit(30, 1)->findAll();
The query that actually gets executed is simple and looks like this:
1 SELECT * FROM `Product` WHERE Product.price BETWEEN :MIN AND :MAX LIMIT 30 OFFSET 1
This tutorial is a modified tutorial from another website/blog that unfortunantly isn’t online anymore, domain is being sold by godaddy.com, so I search my archives to retrieve this on, and post him here, hence a few additions, deletes and rewrites from me.
Cherry 10:58 on 30/12/2009 Permalink |
Hi,I’m trying Yii now.Almost everything could be done with Yii.But all the components,those how I configure ,will run.Something ,like,DB session…
well,my english is so poor!
webscriptz 03:32 on 01/01/2010 Permalink |
I’m a bit torn between speed and programming luxury and because sometimes Yii is poorly documented, nice example code but not all the options are given actually sometimes very few.
I’m currently doing models and testing them in Yii and i can’t get my head really around it, Codeigniter was really easy to use in the model logic but now what’s the logic, Model driven or controller driven because of the AR layer and the model sql query which seems implemented in the controllers. I thought controllers were just a gateway between view and model because it’s the model that usually contains all the logic not the controller.