Global Access To Data

Hello everybody!

I’m starting to learn Yii in this day and i have a little question.

In my website i need to add different data like country, city, difficult level and so on.

This data will be fixed of course, and no user will edit it (i don’t need any crud operation on them).

I want to save all this information in my db (it’s about 7 tables).

Then i need to use this data in all my web site. The easy thing i can do is to create a single model for each table and call Country::model()->findAll() and function like it.

But i would like to know if i can do it in a different way, maybe with only one model or one entering point.

I need to use this data for create new item (that will have for example the country) so in a dropdown list, or to present the list of this data and so on.

Any idea or suggestion to make this thing?

Thanks!

You might create new Class indie components folder and derive the CActiveRecord. Then add a getter for Country, City, etc models in YourActiveRecord.




class YourActiveRecord extends CActiveRecord

{

     public getCountries()

     {

          return Country::model()->findAll();

     }

}



Use this getter in other classes like this:




class AnyModel extends YourActiveRecord

{

     public anyFunction()

     {

          // code

          $var = $this->countries;

          // code

     }

}



Hello, Giov.

You can create a class containing all your lookup data in the components folder (usually protected/components). Declare your data as static member of the class. For example:


class MyLookup extends CComponent

{

	public static $countries = array

	(

		'us' => 'United States',

		'fr' => 'France',

		// etc

	);

	// other lookup data

}



You can access the lookup data from the application as follows:


echo MyLookup::$countries['fr'];



Extending the model from CComponent gives you the possibility to declare also useful getter methods.

Hello everybody and thanks for the help!

@Mohsen Najaflou, this solution need to create a single Model for each table as i have yet done. My idea was to remove lot of Model and make a single access point with a single model.

@Alexandre Rodichevski, your idea is nice, but at the end is a simple property list. The problem with this approach is to call method on this like listAll and similar to use in the views… or not?

Thanks guys!!!

Hi Giov.

You can use the simple property list in your views. For example, in a form:


echo CHtml::dropDownList ('country', '', MyLookup::$countries);

I think, the development and the maintenance are easier using CActiveModel for every lookup table situated in database.

What I normally do is just create a new model for each table lookup and have something like this on each:




class LookupTable extends CActiveRecord

{

    private static $_items;

	

	.

	.

	.

	

	public static function getItems()

	{

		if (self::$_items === null)

		{

			self::$_items = self::model()->findAll();

		}

		return self::$_items;

	}

}



EDIT:

Just realized you wanted a single model approach. If you look at Mohsen Najaflou’s solution, that sort of does exactly what you want

Try playing with the function tableName() in your model, or use query builder.

Thanks to all guys!!!

The idea of Mohsen sounds good! Maybe i can create a global model and write custom method with query builder…

I will try it ;)

Here i am!

Thanks to Mohsen i have a solution!

I post it here, so maybe someone can us it!

Please feel free to give me feedback and modify!

MODEL


class Localizzazione extends CActiveRecord{

	public function tableName(){

		return '';

	}


	public static function model($className=__CLASS__){

		return parent::model($className);

	}


	/**

	 * Here we build the custom query to get all the regioni items

	 */

	public function getRegioni(){

		$cmd= Yii::app()->db->createCommand()

					->select('id, regione')

					->from('regione')

					->order('regione asc')

					->queryAll();

		return $cmd;

	}


	/**

	 * This is the called function.

	 * Get the list of regioni and prepair them as array key=>value

	 */

	public function getRegioniForDropDownList(){

		$items 	= $this->getRegioni();

		$rows 	= array();

		foreach($items as $itmId=>$itmData){

			$rows[$itmData['id']]	= $itmData['regione'];

		}

		return $rows;

	}

}

VIEW


echo CHtml::dropDownList('regioni', 19, Localizzazione::Model()->getRegioniForDropDownList());

Just pass the right name and value to the dropDownList!

Thanks to all!