-
Notifications
You must be signed in to change notification settings - Fork 0
Using Doctrine with Code Igniter
[h3]Learning about Doctrine[/h3]
The best way to learn about Doctrine is to read about it in the manual. Here are some important links.
[url=http://www.phpdoctrine.org/documentation/manual/0_10]Doctrine 0.10 Manual[/url] [url=http://www.phpdoctrine.org/documentation/api/0_10]Doctrine 0.10 API Docs[/url]
[h3]Download Doctrine[/h3]
First we must get the source of Doctrine from svn and place it in the system/database folder.
[code] $ cd system/database $ svn co http://svn.phpdoctrine.org/branches/0.10/lib doctrine $ cd ..
// If you use svn in your project you can set Doctrine // as an external so you receive bug fixes automatically from svn $ svn propedit svn:externals database
// In your favorite editor add the following line // doctrine http://svn.phpdoctrine.org/branches/0.10/lib [/code]
[h3]Setup Doctrine[/h3]
Now we must setup the configuration for Doctrine and load it in system/application/config/database.php
[code] $ vi application/config/database.php [/code]
The code below needs to be added under this line of code
[code] $db['default']['cachedir'] = ""; [/code]
Add this code [code] // Create dsn from the info above $db['default']['dsn'] = $db['default']['dbdriver'] . '://' . $db['default']['username'] . ':' . $db['default']['password']. '@' . $db['default']['hostname'] . '/' . $db['default']['database'];
// Require Doctrine.php require_once(realpath(dirname(FILE) . '/../..') . DIRECTORY_SEPARATOR . 'database/doctrine/Doctrine.php');
// Set the autoloader spl_autoload_register(array('Doctrine', 'autoload'));
// Load the Doctrine connection Doctrine_Manager::connection($db['default']['dsn'], $db['default']['database']);
// Set the model loading to conservative/lazy loading Doctrine_Manager::getInstance()->setAttribute('model_loading', 'conservative');
// Load the models for the autoloader Doctrine::loadModels(realpath(dirname(FILE) . '/..') . DIRECTORY_SEPARATOR . 'models'); [/code]
Now we must make sure system/application/config/database.php is included in your front controller. Open your front controller in your favorite text editor.
[code] $ cd .. $ vi index.php [/code]
Change the last 2 lines of code of index.php with the following
[code] require_once APPPATH.'config/database.php'; require_once BASEPATH.'codeigniter/CodeIgniter'.EXT; ?> [/code]
[h3]Setup Command Line Interface[/h3]
Create the following file: system/application/doctrine and chmod the file so it can be executed. Place the code below in to the doctrine file.
[code] $ vi system/application/doctrine [/code]
Place this code in system/application/doctrine
[code] #!/usr/bin/env php <?php define('BASEPATH','.'); // mockup that this app was executed from ci ;) chdir(dirname(FILE)); include('doctrine.php'); [/code]
Now create the following file: system/application/doctrine.php. Place the code below in to the doctrine.php file.
[code] <?php require_once('config/database.php');
// Configure Doctrine Cli // Normally these are arguments to the cli tasks but if they are set here the arguments will be auto-filled $config = array('data_fixtures_path' => dirname(FILE) . DIRECTORY_SEPARATOR . '/fixtures', 'models_path' => dirname(FILE) . DIRECTORY_SEPARATOR . '/models', 'migrations_path' => dirname(FILE) . DIRECTORY_SEPARATOR . '/migrations', 'sql_path' => dirname(FILE) . DIRECTORY_SEPARATOR . '/sql', 'yaml_schema_path' => dirname(FILE) . DIRECTORY_SEPARATOR . '/schema');
$cli = new Doctrine_Cli($config); $cli->run($_SERVER['argv']); [/code]
Now we must create all the directories for Doctrine to use
[code] // Create directory for your yaml data fixtures files $ mkdir system/application/fixtures
// Create directory for your migration classes $ mkdir system/application/migrations
// Create directory for your yaml schema files $ mkdir system/application/schema
// Create directory to generate your sql to create the database in $ mkdir system/application/sql [/code]
Now you have a command line interface ready to go. If you execute the doctrine shell script with no argument you will get a list of available commands
[code] $ cd system/application $ ./doctrine Doctrine Command Line Interface
./doctrine build-all ./doctrine build-all-load ./doctrine build-all-reload ./doctrine compile ./doctrine create-db ./doctrine create-tables ./doctrine dql ./doctrine drop-db ./doctrine dump-data ./doctrine generate-migration ./doctrine generate-migrations-db ./doctrine generate-migrations-models ./doctrine generate-models-db ./doctrine generate-models-yaml ./doctrine generate-sql ./doctrine generate-yaml-db ./doctrine generate-yaml-models ./doctrine load-data ./doctrine load-dummy-data ./doctrine migrate ./doctrine rebuild-db $ [/code]
On Microsoft Windows, call the script via the PHP binary (because the script won't invoke it automatically: [code]> php.exe doctrine[/code]
[h3]Start Using Doctrine[/h3]
It is simple to start using Doctrine now. First we must create a yaml schema file. (save it at schema with filename like : user.yml) [code]
User: columns: id: primary: true autoincrement: true type: integer(4) username: string(255) password: string(255) relations: Groups: # Relation alias or class name class: Group # Class name. Optional if alias is the class name local: user_id # Local: User.id = UserGroup.user_id. Optional foreign: group_id # Foreign: Group.id = UserGroup.group_id. Optional refClass: UserGroup # xRefClass for relating Users to Groups foreignAlias: Users # Opposite relationship alias. Group hasMany Users
Group: tableName: groups columns: id: primary: true autoincrement: true type: integer(4) name: string(255)
UserGroup: columns: user_id: type: integer(4) primary: true group_id: type: integer(4) primary: true relations: User: local: user_id # Local key foreign: id # Foreign key onDelete: CASCADE # Database constraint Group: local: group_id foreign: id onDelete: CASCADE [/code]
Now if you run the following command it will generate your models in system/application/models
[code] $ ./doctrine generate-models-yaml generate-models-yaml - Generated models successfully from YAML schema [/code]
Now check the file system/application/models/generated/BaseUser.php. You will see a compclass definition like below.
[code] <?php
/**
- This class has been auto-generated by the Doctrine ORM Framework */ abstract class BaseUser extends Doctrine_Record {
public function setTableDefinition() { $this->setTableName('user'); $this->hasColumn('id', 'integer', 4, array('primary' => true, 'autoincrement' => true)); $this->hasColumn('username', 'string', 255); $this->hasColumn('password', 'string', 255); }
public function setUp() { $this->hasMany('Group as Groups', array('refClass' => 'UserGroup', 'local' => 'user_id', 'foreign' => 'group_id'));
$this->hasMany('UserGroup', array('local' => 'id',
'foreign' => 'user_id'));
}
}
// Add custom methods to system/application/models/User.php
<?php
/**
- This class has been auto-generated by the Doctrine ORM Framework */ class User extends BaseUser { public function setPassword($password) { $this->password = md5($password); } }
/**
-
This class has been auto-generated by the Doctrine ORM Framework */ class UserTable extends Doctrine_Table { public function retrieveAll() { $query = new Doctrine_Query(); $query->from('User u'); $query->orderby('u.username ASC');
return $query->execute(); } } [/code]
Now we can create some sample data to load in to our application(this step requires you have a valid database configured and ready to go. The build-all-reload task will drop and recreate the database, create tables, and load data fixtures
Create a file in system/application/fixtures/users.yml
[code] $ vi fixtures/users.yml [/code]
Add the following yaml to the file
User: jwage: username: jwage password: elite1baller [/code]
Now run the build-all-reload task to drop db, build models, recreate
[code] $ ./doctrine build-all-reload build-all-reload - Are you sure you wish to drop your databases? (y/n) y build-all-reload - Successfully dropped database named: "jwage_codeigniter" build-all-reload - Generated models successfully from YAML schema build-all-reload - Successfully created database named: "jwage_codeigniter" build-all-reload - Created tables successfully build-all-reload - Data was successfully loaded [/code]
Now we are ready to use Doctrine in our actual actions. Lets open our system/application/views/welcome_message.php and somewhere add the following code somewhere.
[code] $user = new User(); $user->username = 'zYne-'; $user->setPassword('password'); $user->save();
$userTable = Doctrine::getTable('User'); $user = $userTable->findOneByUsername('zYne-');
echo $user->username; // prints 'zYne-'
$users = $userTable->retrieveAll();
echo $users->count(); // echo '2'' foreach ($users as $user) { echo $user->username; } [/code]