In this episode of the series, we will continue building our Message Board project. First we will have a quick overview of Doctrine Model Relationships. Then we will create Models for our Message Board, such as: Forums, Threads, Posts etc… with proper relationships. Finally we will learn how to add data into such Models.
"CodeIgniter and Doctrine from Scratch" Series:
Doctrine Model Relationships (a quick overview)
One of the key features of Doctrine is the handling of Relationships between Models. At this point in our project, we will start utilizing it.
On a typical Message Board:
- There are Forums
- Forums have Threads
- Threads have Posts
- Users have Posts

We will learn how to define these relationships in our Models. Doctrine supports the following types of relationships:
- One to Many (or Many to One)
- One to One
- Many to Many
- Tree Structure
- Nest Relations
Today we will be talking about only the first two.
Foreign Keys
To setup relationships between models (and tables in the database), we need to have certain fields in our tables. These are used as Foreign Keys.
For example, if each Post belongs to a User, we need a user_id field in the Post table. We can specify this in our model:
class Post extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn('content', 'string', 65535);
$this->hasColumn('user_id', 'integer');
}
}
But to specify the type of relationship, we are going to have to do more than that.
One to Many Relationships
Just like the name suggests, this creates a relationship between one instance of a Model and multiple instances of another Model.
For example: one User has many Posts.
In Doctrine, this kind of relationship is setup using the hasOne() and hasMany() functions.
Post Example:
class Post extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn('content', 'string', 65535);
$this->hasColumn('user_id', 'integer');
}
public function setUp() {
$this->hasOne('User', array(
'local' => 'user_id',
'foreign' => 'id'
));
}
}
hasOne() says that the Post is associated with one User. The first parameter is the Model name and the second parameter is an array that sets the foreign keys.
It links the two Models by the user_id field in the local Model (i.e. Post), with the id field in the foreign Model (i.e. User).
Now we can access the User object for a post like this: $post->User. We’ll see more of that later.
User Example:
class User extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn('username', 'string', 255, array('unique' => 'true'));
$this->hasColumn('password', 'string', 255);
}
public function setUp() {
$this->hasMany('Post as Posts', array(
'local' => 'id',
'foreign' => 'user_id'
));
}
}
On this side of the relationship, there are no additional fields for the foreign key. But we still define it by the hasMany() call.
The first parameter looks a bit different this time. When we say Post as Posts, we link to the Model named Post, but we name the property Posts.
This way we are going to access it like $user->Posts, instead of $user->Post. This is just a matter of preference, because it sounds better.
Note: As a rule of thumb, the Model that has the hasOne() call is the one with the foreign key field. (Post.user_id in this case).
One to One Relationships
This type of relationship is used when each Model is linked to only one instance of the other Model.
For example, if you have separate Models/Tables for User and Email, and if you want each User to have only one Email, you might use this.
The syntax is exactly the same as the One to Many Relationships, but this time both Models call the hasOne() function, instead of hasMany().
for more info
This is all we needed to know to continue our project for now. But if you want to find out about all types of relationships in Doctrine, you can read the whole documentation section on this subject here.
Let’s Create Some Models
Let’s use what we just learned to create our new Models.
Note: I would like to build this project similar to the CodeIgniter Message Board. They also seem to have Categories, that contain multiple Forums, so we are going to create a Model for that too.
Category Model
- Create: system/application/models/category.php
<?php
class Category extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn('title', 'string', 255);
}
public function setUp() {
$this->hasMany('Forum as Forums', array(
'local' => 'id',
'foreign' => 'category_id'
));
}
}
Looks simple. We have a Category Model that has a title, and can have many Forums. Also we are expecting that the Forum Model to have a field named category_id.
Forum Model
- Create: system/application/models/forum.php
<?php
class Forum extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn('title', 'string', 255);
$this->hasColumn('description', 'string', 255);
$this->hasColumn('category_id', 'integer', 4);
}
public function setUp() {
$this->hasOne('Category', array(
'local' => 'category_id',
'foreign' => 'id'
));
$this->hasMany('Thread as Threads', array(
'local' => 'id',
'foreign' => 'forum_id'
));
}
}
As expected, we have a category_id field for the foreign key.
Also we have 2 relationships now. First one is with Category Model, as Forums have (or belong to) a single Category. The second one is with Thread Model. Each Forum can have many Threads.
Thread Model
- Create: system/application/models/thread.php
<?php
class Thread extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn('title', 'string', 255);
$this->hasColumn('forum_id', 'integer', 4);
}
public function setUp() {
$this->hasOne('Forum', array(
'local' => 'forum_id',
'foreign' => 'id'
));
$this->hasMany('Post as Posts', array(
'local' => 'id',
'foreign' => 'thread_id'
));
}
}
Post Model
- Create: system/application/models/post.php
<?php
class Post extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn('content', 'string', 65535);
$this->hasColumn('thread_id', 'integer', 4);
$this->hasColumn('user_id', 'integer', 4);
}
public function setUp() {
$this->actAs('Timestampable');
$this->hasOne('Thread', array(
'local' => 'thread_id',
'foreign' => 'id'
));
$this->hasOne('User', array(
'local' => 'user_id',
'foreign' => 'id'
));
}
}
Notice this time we have 2 foreign keys. Because a Post belongs to a Thread, and also belongs to a User.
User Model
We already have this Model, we are just making changes.
- Edit: system/application/models/user.php
<?php
class User extends Doctrine_Record {
// ...
public function setUp() {
$this->setTableName('user');
$this->actAs('Timestampable');
$this->hasMutator('password', '_encrypt_password');
$this->hasMany('Post as Posts', array(
'local' => 'id',
'foreign' => 'user_id'
));
}
//...
}
Create the Tables
Remember our Controller that creates Tables from Models? It’s time to use that again.
- Go to: http://localhost/ci_doctrine/doctrine_tools/create_tables
- Press the button, and it should create the tables.
- Look at phpmyadmin at: http://localhost/phpmyadmin.

Looks great!
Now let’s see how we can add some data using these Models.
Creating Records
We are going to write a quick test controller to demonstrate how we can add data.
- Create: system/application/controllers/test.php
<?php
class Test extends Controller {
function index() {
$category = new Category();
$category->title = "The CodeIgniter Lounge";
$category->save();
$forum = new Forum();
$forum->title = "Introduce Yourself!";
$forum->description = "Use this forum to introduce yourself to the CodeIgniter community, or to announce your new CI powered site.";
$forum->Category = $category;
$forum->save();
}
}
Do you see how intuitive it is?
$forum->Category represents the relationship that the Forum object has with the Category Model. We can directly assign a Category object to it to link them.
Let’s expand this so we have a bit more data.
- Edit: system/application/controllers/test.php
<?php
class Test extends Controller {
function index() {
$category = new Category();
$category->title = "The CodeIgniter Lounge";
$forum = new Forum();
$forum->title = "Introduce Yourself!";
$forum->description = "Use this forum to introduce yourself to the CodeIgniter community, or to announce your new CI powered site.";
// add category to the forum
$forum->Category = $category;
$forum2 = new Forum();
$forum2->title = "The Lounge";
$forum2->description = "CodeIgniter's social forum where you can discuss anything not related to development. No topics off limits... but be civil.";
// you can also add the other way around
// add forum to the category
$category->Forums []= $forum2;
// a different syntax (array style)
$category2 = new Category();
$category2['title'] = "CodeIgniter Development Forums";
$forum3 = new Forum();
$forum3['title'] = "CodeIgniter Discussion";
$forum3['description'] = "This forum is for general topics related to CodeIgniter";
$forum4 = new Forum();
$forum4['title'] = "Code and Application Development";
$forum4['description'] = "Use the forum to discuss anything related to programming and code development.";
$category2['Forums'] []= $forum3;
$category2['Forums'] []= $forum4;
// flush() saves all unsaved objects
$conn = Doctrine_Manager::connection();
$conn->flush();
echo "Success!";
}
}
We just created 2 categories, and 2 forums in each of them, in a few different ways.
- Line 21: We add a Forum to the Category, instead of the other way around. But this time, since $category->Forums contains multiple Forums, we push to it like you would to an array, instead of direct assignment like on line 13.
- Lines 25-37: Here you can see how we can access all elements of the Doctrine Model objects like array elements. Some people prefer this syntax.
- Lines 40-41: Instead of calling save() on every single object, we can just use flush() to save everything.
Let’s test this.
You should see the success message:
Success!
Now let’s look at the category table:

You can see our new 2 categories, with id’s 1 and 2. Let’s see if the forums got the correct associations.
Look at the forum table:

Everything looks good! The Forums each have proper category_id’s assigned.
Stay Tuned
Today we learned about one of main features of Doctrine. We were able to create foreign key relationships without using any queries whatsoever! That is one of the nice things about using an ORM like Doctrine. I hope you are able to see how much time you can save by developing like this.
In the next episode we will continue on our project, with a little more CodeIgniter stuff.
See you next time!

#1 by shin on November 13th, 2009
| Quote
Another excellent post. I’d like to see more article like this.
I’d like to request a simple project management with CI and doctorine for near future. Project management also has different users and projects and I think it will suit with CI/Doc combination.
#2 by BB on November 13th, 2009
| Quote
these are really seriously cool tutorials.
could you pls fix the css so I can print ‘em out correctly?
many thx.
#3 by Drew Spencer on November 13th, 2009
| Quote
Loving these tutorials – just devoured them all on a morning!
Can’t wait for the next installment. Keep up the great work.
#4 by BradM on November 13th, 2009
| Quote
@BB have you ever tried Readability?
http://lab.arc90.com/experiments/readability/
Its great for printing and reading posts online. Gets rid of the clutter. No installation, works great.
#5 by BB on November 15th, 2009
| Quote
thanks for the tip BradM.
you saved the day
#6 by Burak on November 15th, 2009
| Quote
I just tested it, it seems like it deletes the code sections, which is not good.
I’m using a free wordpress theme, it didn’t come with a print CSS. I’ll look into it when I get chance, to see if there is another solution.
#7 by Mike on February 10th, 2010
| Quote
it seems to print ok in IE
By the way, great work. This is probably the best tutorial on doctrine available, with or without CI.
#8 by Robin Mitra on May 8th, 2010
| Quote
Thanks for the link Brad! Readability seems really cool!
Burak, awesome tutorials man! You are an excellent teacher!
#9 by zack on November 13th, 2009
| Quote
Can’t get enough. You should write a book.
#10 by Emre on November 14th, 2009
| Quote
One more great tutorial by you, Burak! Hats off to you..
I think there is a typo at the begining of the tutorial. It is where you are talking about one-to-many relationship. At the User model code:
9 $this->hasMany(‘Post as Posts’, array(
10 ‘local’ => ‘id’,
11 ‘foreign’ => ‘post_id’
12 ));
foreign value seems ‘post_id’, but it should be ‘user_id’ I think.
#11 by Burak on November 14th, 2009
| Quote
Nice catch, thank you. It’s corrected now.
#12 by Kerran on November 14th, 2009
| Quote
Bring on day 7
#13 by Steve Larch on November 15th, 2009
| Quote
Great tutorials, Burak. I just started working with PHP frameworks this weekend. I was beginning to think I’d picked the wrong horse (CodeIgniter) until I came across your site. Thanks for the great information!
#14 by Emre on November 15th, 2009
| Quote
I wonder if we will be able to make nested posts for this example project. I mean hiearchical posts that one post may have children posts which are reply for parent post?
As an example: your wordpress’ hierarchical comment structure..
It would be very useful to learn Doctrine’s nested set structure for handling trees in database.
#15 by Burak on November 15th, 2009
| Quote
Yea, Doctrine supports those kinds of structures. There are a few different ways of handling it. I’m trying to think of something that will use it in this project. It might be either nested posts or nested forums.
#16 by Emre on November 15th, 2009
| Quote
Thank you for the explanation. We are really waiting for it.
#17 by chonlatee on November 15th, 2009
| Quote
sorry my English , Thank you for your article it’s useful and i hope you will post again. i am waiting
#18 by Drew Spencer on November 16th, 2009
| Quote
Burak, when is part 7 coming out?
Also, I was wondering if you might do something with jQuery as well? These 3 combined would be really useful.
Thanks again.
#19 by Albert on November 16th, 2009
| Quote
Very carefully and thoroughly developed tutorial. Excellent introduction to Doctrine and Code Igniter.
Hope you’ll consider contacting their project group and offering it for their tutorial library.
Thank you for taking the time to produce these.
#20 by Carlos on November 16th, 2009
| Quote
God, you really know how to explain hard to understand things.
For me your tutorials are top quality learning material.
Please keep up with your hard work.
Thankyou!
#21 by yfi on November 19th, 2009
| Quote
Wow, these are excellent. They read like a novel and you have a real gift for clarity.
Now, I myself am wondering how to create a search function in CI. It’s such a common feature in web applications but I haven’t seen many tutorials that would tell the story the way you do.
After reading episode 1, I browsed the doctrine website and noticed the searchable and taggable extensions. Is there any way you could cover those?
Thank You.
#22 by Burak on November 19th, 2009
| Quote
Searchable might be useful in this project, but I’m not sure how Taggable would apply to a Message Board.
#23 by ABACA on November 30th, 2009
| Quote
That’s great. Just the way I need it in my project. Can’t wait to see the next tuts. Thanks.
#24 by Kamil Grzegorczyk on December 13th, 2009
| Quote
Where CRUD methods should be called?
When I was using AR – I was calling model functions from controller to delete a record for example.
Now I dont know how to do it using doctrine. For example deleting from controller works – but i don;t think that this is a good idea – what should i do to call function model->delete from controller – old way doesn;t work…
#25 by Burak on December 13th, 2009
| Quote
I am not sure if I understand the question correctly. But to delete a User with a given id for example, you can do this:
Doctrine::getTable(‘User’)->find($user_id)->delete();
If you already have the user object, you can directly call delete():
$user->delete();
#26 by Kamil Grzegorczyk on December 13th, 2009
| Quote
yes I was doing like that and this method worked for me – but I’m calling it from inside a controller – is it a good way? I always thought that this kind of operations (operating on database) should be done in model.
So this is the diffrence between Active record and ORM approach?
#27 by Kamil Grzegorczyk on December 13th, 2009
| Quote
OK, Now I see that I got lost – but now after little stop I think that this is the same as old approach (using AR directives) but everything is managed for me by Doctrine methods – so it is actually done in model…
Thanks
#28 by Burak on December 13th, 2009
| Quote
Yeah, delete() is already implemented in the Doctrine class, so it is already abstracted.
But if you need to do complex DQL queries, you can put that in a function inside the Model. There is an example of that in the Day 9 article that I just posted.
#29 by Naim on December 15th, 2009
| Quote
COULD SOMEONE EXPLAIN THIS ERROR PLEASE?
Fatal error: Uncaught exception ‘Doctrine_Export_Exception’ with message ‘SQLSTATE[HY000]: General error: 1005 Can’t create table ‘safarista-cms.#sql-160c_4d’ (errno: 150). Failing Query: “ALTER TABLE post ADD CONSTRAINT post_thread_id_thread_id FOREIGN KEY (thread_id) REFERENCES thread(id)”. Failing Query: ALTER TABLE post ADD CONSTRAINT post_thread_id_thread_id FOREIGN KEY (thread_id) REFERENCES thread(id)’ in C:\wamp\www\safarista-cms\application\plugins\doctrine\lib\Doctrine\Export.php:1219 Stack trace: #0 C:\wamp\www\safarista-cms\application\plugins\doctrine\lib\Doctrine\Export.php(1100): Doctrine_Export->exportClasses(Array) #1 C:\wamp\www\safarista-cms\application\plugins\doctrine\lib\Doctrine\Core.php(889): Doctrine_Export->exportSchema(NULL) #2 C:\wamp\www\safarista-cms\application\controllers\doctrine_tools.php(11): Doctrine_Core::createTablesFromModels() #3 C:\wamp\www\safarista-cms\system\codeigniter\CodeIgniter.php(236): Doctrine_Tools->create_tables() #4 C:\wamp\www\safarista-cms\index.php(115): require_onc in C:\wamp\www\safarista-cms\application\plugins\doctrine\lib\Doctrine\Export.php on line 1219
#30 by Burak on December 15th, 2009
| Quote
That happens when you try to create a foreign key between two columns that are not the same exact structure.
For example if one column is INT and the other is BIGINT.. Or if one column is UNSIGNED and the other one isn’t etc..
Seems like your error has to do with post.thread_id and thread.id
#31 by Marcello Romani on January 5th, 2010
| Quote
Hi, the problem is that we are setting up foreign key constraints against automatically created ‘id’ fields.
Remember from the first tutorial that the ‘id’ column is automatically created by Doctrine (in doctrine_pi there is a setting for this).
If you DESCRIBE the Forum table, for example, you’ll see that the ‘id’ column is UNSIGNED. By contrast, when you define the column ‘forum_id’ in the Post model, you probably just wrote ‘integer’. So the end result is a foreign key constraint where one field is ‘integer’ and the other one is ‘integer unsigned’. Thus the error.
Solution: add the ‘unsigned’ option to the foreign key, e.g.:
$this->hasColumn(‘forum_id’, ‘integer’, 4, array(‘unsigned’ => true));
HTH
#32 by Marcello Romani on January 5th, 2010
| Quote
This is the relevant line in system/application/plugins/doctrine_pi.php:
Doctrine_Manager::getInstance()->setAttribute(Doctrine::ATTR_DEFAULT_IDENTIFIER_OPTIONS, array(‘name’ => ‘id’, ‘type’ => ‘integer’, ‘length’ => 4));
#33 by Burak on January 9th, 2010
| Quote
In doctrine_pi.php I put this line too:
Doctrine_Manager::getInstance()->setAttribute(
Doctrine::ATTR_DEFAULT_COLUMN_OPTIONS,
array(‘notnull’ => true, ‘unsigned’ => true));
That applies to all columns. So it should already be defaulting to unsigned.
#34 by Christian Voigt on August 6th, 2010
| Quote
If, for example, your local key is ’4′ and the foreign key is declared as ‘null’, then you will get that exact error.
#35 by Naim on December 15th, 2009
| Quote
I would like to know how to implement the EMAIL and GROUPS functionality having enjoyed the way CI-D is relating things. am totally hew to Doctrine.
Burak is probably one guy who learned English as a fifth language. Native English speakers don’t explain things like this. Simple, easy to understand and straight to the point. No big ambiguous Words. Or your teacher was a good one, OR you just have a talent for teaching. Do you have a donate button?
#36 by Burak on December 15th, 2009
| Quote
I learned it as a third language actually, so you’re pretty close
By GROUPS, do you mean GROUP BY in queries? That is done with DQL. You can see some examples of that in the further articles.
I’m not sure what you mean by EMAIL functionality. If you are talking about input validation, you can take a look at this: http://www.doctrine-project.org/documentation/manual/1_2/en/data-validation#examples:email
#37 by Gareth Price on December 23rd, 2009
| Quote
Hello, Quick question; how would I go about getting a text column, for say, topic text? I can’t see a suitable option in doctrine..
#38 by Burak on December 23rd, 2009
| Quote
Just use a ‘string’ type column with a high length value, for example 10000. It should turn into a TEXT column.
#39 by Gareth Price on December 23rd, 2009
| Quote
Wicked, thank you!
#40 by esryl on January 9th, 2010
| Quote
@27, @28, @29
I am using these tutorials to craft my own little CMS, and ran across the same problem as @27.
The culprit was, autogenerated IDs are created as INT(10), while the key associations in Many to Many are created as BIGINT(20). When I manually changed these to INT(10), the script reran without problem.
Any ideas how to automatically get Doctrine to use matching Data Types?
#41 by Burak on January 10th, 2010
| Quote
In the plugin file (doctrine_pi.php), I set the id fields to be 4byte INT by default. You can change that to BIGINT (i.e. 8 byte integer) if you want to use that.
I don’t think you can tell Doctrine to automatically match the column types on the foreign keys.
#42 by Umut on January 11th, 2010
| Quote
Hi, you have a really nice series going on!
I just like to know how you was able to change the default(?) coallition latin1_swedish_ci to utf8_general_ci. It seems when I create tables with the inbuilt doctrine function I get those swedish cells.
#43 by Umut on January 11th, 2010
| Quote
Selamlar!, you have a really nice series going on!
I just like to know how you was able to change the default(?) coallition latin1_swedish_ci to utf8_general_ci. It seems when I create tables with the inbuilt doctrine function I get those swedish cells.
#44 by Burak on January 11th, 2010
| Quote
When I created the ci_doctrine database, I set it to utf8 default. That’s why the tables defaulted to utf8 as well.
You can explicitly set it like this if you want to (in setTableDefinition()):
$this->option(‘collate’, ‘utf8_unicode_ci’);
$this->option(‘charset’, ‘utf8′);
#45 by Umut on January 12th, 2010
| Quote
Thanks!, figured it out eventually! Thou I tried everything. Only to notice that i hadn’t changed the collation option when I created the database
#46 by krzysko on February 15th, 2010
| Quote
Hi.
I try made a relationship many to many and I get this:
Doctrine_Export_Exception: SQLSTATE[42703]: Undefined column: 7 BŁĄD: kolumna “id” określona w kluczu obcym nie istnieje. Failing Query: “ALTER TABLE poku_order_customer ADD CONSTRAINT poku_order_customer_id_poku_order_id FOREIGN KEY (id) REFERENCES poku_order(id) NOT DEFERRABLE INITIALLY IMMEDIATE”. Failing Query: ALTER TABLE poku_order_customer ADD CONSTRAINT poku_order_customer_id_poku_order_id FOREIGN KEY (id) REFERENCES poku_order(id) NOT DEFERRABLE INITIALLY IMMEDIATE in /var/www/postkurier_prog/ci_ver_0.1/system/application/plugins/doctrine/lib/Doctrine/Export.php on line 1219
If is necessary I can put my source code models. Any ideas?:)
#47 by krzysko on February 15th, 2010
| Quote
Sorry for that above the problem is solved.
#48 by bresson on March 16th, 2010
| Quote
I’m very impressed with your tutorial – definitely on the level of professional teaching and publication. I look forward to seeing much more from you, whether in print or online.
#49 by Kerran on March 19th, 2010
| Quote
Hey boys and girls. Nice tut as always however after spending 20 minutes trouble shooting various ‘hasMany’ & ‘hasOne’ relationships I thought there must be an even easier way. Is it possible to use the fantastic Doctrine Schema function and enter the relationships using only the model name?
#50 by Burak on March 28th, 2010
| Quote
I believe there is some amount of auto detection when using YAML schema files, so you can define a relationship just by providing the model name as long as foreign keys are named appropriately.
#51 by Broncha on May 14th, 2010
| Quote
Nice tutorial.This is the best series of tutorials I’ve got in the Internet. Doctrine makes it real easy to build application.
Thanks.Waiting for the rest of the tutorials from day12
#52 by J Manninen on May 23rd, 2010
| Quote
Hi,
Just a “quick” question about relationships in doctrine. Ie. if you create table called paper, and it belongs to a category, so i would define hasOne in paper-model, and hasMany in category -table.
I have done that, but when i try to save paper without giving it a category value, it gives me a error. I haven’t defined that category is required value. But is it so, that if you define relationships, the value becomes required?
I also have defined created_by field in paper-model, and it links to user-table. But it should not be required, but it doesnt allow me to save if created_by is not set.
#53 by J Manninen on May 26th, 2010
| Quote
Ok, thats fixed. It seems that InnoDB doesnt accept empty values for relations. I changed to MyISAM and now it works.
#54 by Darel on June 25th, 2010
| Quote
Burak,
Your Test model has Categories assigned to forums in the code, but I don’t see the relationships in your diagram. Was there a reason for that?
#55 by Burak on June 25th, 2010
| Quote
The diagram was just an example. Not the exact plan for the code.
#56 by Darel on June 25th, 2010
| Quote
Burak, thanks for the fast response. I’m really loving this Tutorial!
#57 by musonic on July 7th, 2010
| Quote
Firstly, fantastic tutorials. The best I’ve seen. I’m having some problems though and hope you can help. I’m trying to set up a one to one relationship between a Login and a User table. They are linked by the id column in the User table. For some reason when i create the tables the column user_id in the Login table will not create in the way I expect. If I simply declare “integer” a column with type bigint(20) is created. If I use “int” then a column with type “int(11)” is created and the same happens if I specify a length. The automatically created id column in the User table is of type “int(10)” and is unsigned. Even though cols are meant to be unsigned by default my user_id is not. Any ideas why this is happening?
#58 by ivankruel on July 13th, 2010
| Quote
Fatal error: Uncaught exception ‘Doctrine_Table_Exception’ with message ‘Unknown relation alias detalle’ in C:\wamp\www\pueblareceta\system\plugins\doctrine\Doctrine\lib\Doctrine\Relation\Parser.php:237 Stack trace: #0 C:\wamp\www\pueblareceta\system\plugins\doctrine\Doctrine\lib\Doctrine\Relation\Parser.php(235): Doctrine_Relation_Parser->getRelation(‘detalle’, false) #1 C:\wamp\www\pueblareceta\system\plugins\doctrine\Doctrine\lib\Doctrine\Table.php(1001): Doctrine_Relation_Parser->getRelation(‘detalle’, true) #2 C:\wamp\www\pueblareceta\system\plugins\doctrine\Doctrine\lib\Doctrine\Query.php(1736): Doctrine_Table->getRelation(‘detalle’) #3 C:\wamp\www\pueblareceta\system\plugins\doctrine\Doctrine\lib\Doctrine\Query\From.php(88): Doctrine_Query->load(‘c.detalle d’) #4 C:\wamp\www\pueblareceta\system\plugins\doctrine\Doctrine\lib\Doctrine\Query\Abstract.php(2077): Doctrine_Query_From->parse(‘LEFT JOIN c.det…’) #5 C:\wamp\www\pueblareceta\system\plugins\doctrine\Doctrine\lib\Doctrine\Query.php(1160): Doctrine_Query_Abst in C:\wamp\www\pueblareceta\system\plugins\doctrine\Doctrine\lib\Doctrine\Relation\Parser.php on line 237
#59 by ivankruel on July 13th, 2010
| Quote
sorry forgot the comment, i’m stock in here any adia about the error:
$query = new Doctrine_Query();
$query->select(‘c.fecha, c.folio, c.sps, c.nompac, d.clave_c, d.corto, d.canreq, d.cansur’);
$query->from(‘captura c’);
$query->leftJoin(‘c.detalle d’);
$query->where(‘c.idsuc=?’, $this->input->post(‘sucursal’));
$query->addWhere(‘c.fecha between ? and ?’, array($per[0]['perini'], $per[0]['perfin']));
$query->orderBy(‘c.fecha, c.sps’);
$query->setHydrationMode(Doctrine::HYDRATE_ARRAY);
$query->execute();
#60 by cristi on July 14th, 2010
| Quote
hy.
i have a question
let say we have 2 tables:
1. user – [id] [username][password][group_id]
2. group – [id] [name]
if I say user has one group and group has many users – conditions
if i try to do something like here:
$u->username= ‘user1′;
$u->Group->name = “grup1″;
$u->save();
it will insert in table user 1 record and in column group_id value 1.
Problem is if i want to add another user to same group, instead to insert a new line in only table user with value 1 on group_id field, i get inserted a row in user with group_id2 and in group another row with id 2 and same name.
Any help will be apreciated.
Thanks
#61 by cristi on July 14th, 2010
| Quote
so after first insert i have in users table:
id username group_id
1 user1 1
and in group table:
id name
1 group 1
and after second insert i have in users table:
id username group_id
1 user1 1
1 user2 2
and in group table:
id name
1 group 1
2 group 1 ( – this is the problem, group 1 already exists, why is added again and is not use his id? )
i hope this time my explanation are better
#62 by Burak on July 14th, 2010
| Quote
Try setting your group name field to unique, in your Model.
#63 by cristi on July 14th, 2010
| Quote
i’ve tried, but in that situation if i try to add a new user to that group i get a “duplicate entry error”.
maybe u have a better idea, i just want to have groups with users, and every user to be part of just one group.
#64 by cristi on July 22nd, 2010
| Quote
guys, i need u help in previous situation, please!
#65 by Ahmed Tawfik on August 15th, 2010
| Quote
Thanks Burak , It’s a good information
#66 by Armand van der Walt on August 30th, 2010
| Quote
Hi
Thanks for great tut.
But unfortunately I have a problem with my relations. I can’t figure what the problem is, and its most likely something stupid that I did. Any help will be great.
Fatal error: Uncaught exception ‘Doctrine_Connection_Mysql_Exception’ with message ‘SQLSTATE[23000]: Integrity constraint violation: 1452 Cannot add or update a child row: a foreign key constraint fails (`ci_doctrine`.`post`, CONSTRAINT `post_companys_id_companys_id` FOREIGN KEY (`companys_id`) REFERENCES `companys` (`id`))’ in C:\wamp\www\ci_doctrine\system\application\plugins\doctrine\lib\Doctrine\Connection.php:1082 Stack trace: #0 C:\wamp\www\ci_doctrine\system\application\plugins\doctrine\lib\Doctrine\Connection\Statement.php(269): Doctrine_Connection->rethrowException(Object(PDOException), Object(Doctrine_Connection_Statement)) #1 C:\wamp\www\ci_doctrine\system\application\plugins\doctrine\lib\Doctrine\Connection.php(1042): Doctrine_Connection_Statement->execute(Array) #2 C:\wamp\www\ci_doctrine\system\application\plugins\doctrine\lib\Doctrine\Connection.php(687): Doctrine_Connection->exec(‘INSERT INTO pos…’, Array) #3 C:\wamp\www\ci_doctrine\system\application\plugins\doctrine\lib\Doctrine\Connection\UnitOfWork.p in C:\wamp\www\ci_doctrine\system\application\plugins\doctrine\lib\Doctrine\Connection.php on line 1082
The code:
class Post extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn(‘content’, ‘string’, 65535);
$this->hasColumn(‘category_id’, ‘integer’, 4);
$this->hasColumn(‘companys_id’, ‘integer’, 4);
}
public function setUp() {
$this->actAs(‘Timestampable’);
$this->hasOne(‘Category’, array(
‘local’ => ‘category_id’,
‘foreign’ => ‘id’
));
$this->hasOne(‘Companys’, array(
‘local’ => ‘companys_id’,
‘foreign’ => ‘id’
));
}
}
class Category extends Doctrine_Record {
public function setTableDefinition() {
$this->hasColumn(‘title’, ‘string’, 255);
}
public function setUp() {
$this->hasMany(‘Post as Posts’, array(
‘local’ => ‘id’,
‘foreign’ => ‘category_id’
));
}
}
class Companys extends Doctrine_Record{
public function setTableDefinition() {
$this->hasColumn(‘companyName’, ‘string’, 255, array(‘unique’ => ‘true’));
$this->hasColumn(‘contactPerson’, ‘string’, 255);
$this->hasColumn(‘contactNumber’, ‘string’, 255);
$this->hasColumn(‘mobileNumber’, ‘string’, 255);
$this->hasColumn(‘email’, ‘string’, 255, array(‘unique’ => ‘true’));
$this->hasColumn(‘password’, ‘string’, 255);
$this->hasColumn(‘category_of’, ‘string’, 255);
}
public function setUp() {
$this->setTableName(‘companys’);
$this->actAs(‘Timestampable’);
$this->hasMutator(‘password’, ‘_encrypt_password’);
$this->hasMany(‘Post as Posts’, array(
‘local’ => ‘id’,
‘foreign’ => ‘companys_id’
));
}
protected function _encrypt_password($value)
{
$salt = ‘#*seCret!@-*%’;
$this->_set(‘password’, md5($salt . $value));
}
}
#67 by Armand van der Walt on August 30th, 2010
| Quote
I have narrowed my problem down to where in the post class I had the relationship with the company.
This is the code that gives me the error:
$this->hasOne(‘Companys’, array(
‘local’ => ‘companys_id’,
‘foreign’ => ‘id’
));
#68 by Armand van der Walt on August 30th, 2010
| Quote
Found the problem, its related to not having assigned something to $post->Companys
#69 by Paul on September 4th, 2010
| Quote
Hi there,
first of all thanks for this great tutorial!
I am having a little trouble with something though… I want to delete a table that I created following this tutorial, because I want to change some parameters in setTableDefinition (stuff like null, notnull, unique, etc.).
But when I try to drop the table I get this error message from PhpMyAdmin:
“Cannot delete or update a parent row: a foreign key constraint fails”
How do I remove the foreign key constraint?
#70 by tomotechi on October 23rd, 2010
| Quote
Hi Everyone,
I ran into a little problem today that is somewhat relevant to this thread. I find myself coming back here for reference material on using Doctrine with Codeigniter – so hopefully what I learned today will help the next person coming along. This is in regards to saving related records simultaneously with Doctrine. The example in the reference manual here:
http://www.doctrine-project.org/projects/orm/1.2/docs/manual/working-with-models/en#dealing-with-relations
provides an example with a User() object that has a one to one relationship with an Email() object. The manual suggests that the following is possible:
the save() method would then create both the new user record and email record in the database at the same time. while this is true, i have finally arrived at the conclusion to that if an inverse one-to-one relationship exists, Doctrine fails to create the records. Here is my example:
a Contact model definition:
class Contact extends Doctrine_Record { public function setTableDefinition() { $this->hasColumn('name', 'string'); $this->hasColumn('phone', 'string'); $this->hasColumn('email', 'string'); $this->hasColumn('is_recipient', 'string'); $this->hasColumn('address1', 'string'); $this->hasColumn('address2', 'string'); $this->hasColumn('city', 'string'); $this->hasColumn('state', 'string'); $this->hasColumn('zip', 'string'); $this->hasColumn('username', 'string'); $this->hasColumn('property_id', 'integer', 4); $this->hasColumn('contact_type_id', 'integer', 4); } public function setUp() { $this->setTableName('contact'); $this->actAs('Timestampable'); $this->hasOne('property', array( 'local' => 'property_id', 'foreign' => 'id' )); $this->hasOne('contact_type', array( 'local' => 'contact_type_id', 'foreign' => 'id' )); } }the corresponding Property model:
class Property extends Doctrine_Record { public function setTableDefinition() { $this->hasColumn('number', 'string'); $this->hasColumn('address1', 'string'); $this->hasColumn('address2', 'string'); $this->hasColumn('city', 'string'); $this->hasColumn('state', 'string'); $this->hasColumn('zip', 'string'); $this->hasColumn('primary_contact_id', 'integer', 4); $this->hasColumn('last_modifier_id', 'integer', 4); } public function setUp() { $this->setTableName('property'); $this->actAs('Timestampable'); $this->hasMany('contact', array( 'local' => 'id', 'foreign' => 'property_id' )); $this->hasMany('violation', array( 'local' => 'id', 'foreign' => 'property_id' )); $this->hasOne('contact as primary_contact', array( 'local' => 'primary_contact_id', 'foreign' => 'id' )); $this->hasOne('user as last_modifier', array( 'local' => 'last_modifier_id', 'foreign' => 'id' )); } }Doctrine fails to insert when I try this:
finally i tried to work around what seemed like a key constraint problem with this:
this then DOES create the Property object in the db, with the primary_contact_id field properly set to the new Contact id. However, on the other side of the relationship – the ‘property_id’ field for the new Contact record is set to ’0′ – leading me to the conclusion that the inverse one-to-one relationship is causing the problem.
I have programming around this fairly easily with a subsequent fetch and update of the contact record, but if anyone knows of a solution, or sees some error in my code that is causing this, please do say so : )
thx!
#71 by tomotechi on October 23rd, 2010
| Quote
my dirty fix:
// make a new property, override key checks, save. $p = new Property(); Doctrine_Manager::connection()->execute('SET FOREIGN_KEY_CHECKS = 0'); $p->save(); // now proceed using the saved property object $pc = $p->primary_contact; // and this becomes possible $p->primary_contact->property_id = $p->id; $p->save();#72 by Ryan Coutinho on November 2nd, 2010
| Quote
Hi all,
I have created 2 classed named:
Account and Numbers
relation between them = 1 to many -> 1 Account has more Numbers.
i have done an entry on both but want to add another number to the existing account. The account id = 3.
What is the best way to do this?
findOneById($id));
$number = new Number();
$number->msisdn = “5970843″;
$number->Account = $account;
$number->Bal = $bal;
$number->save();
}
}
this code inserts a new number but with NULL for account number which should be 3.
any help?
#73 by Brett on January 1st, 2011
| Quote
How do you create two foreign keys that point to the same primary key in the same model?
For instance, you have a CreatedUserID and ModifiedUserID.
In my setup() function, I have the following:
$this->hasOne(‘User’, array(
‘local’ => ‘CreatedUserID’,
‘foreign’ => ‘UserID’
));
$this->hasOne(‘User’, array(
‘local’ => ‘ModifiedUserID’,
‘foreign’ => ‘UserID’
));
It only creates a FK for ModifiedUserID or whatever I have as the last one defined.
any help?
#74 by Koen on January 8th, 2011
| Quote
Great tut! thanks!
Any plans on doing a tutorial on many-to-many relations, and how to add or remove date in those?
Cheers, Koen
Pingback: CodeIgniter and Doctrine | Me and My Self
Pingback: Can’t create relationship using doctrine+CI « Mi Casa Es Suit Casa
Trackback: women with big butts
Pingback: CodeIgniter and Doctrine from Scratch » CodeIgniter Resources
Pingback: CodeIgniter and Doctrine from scratch. | 世界是平的
Pingback: CodeIgniter and Doctrine from scratch. | 世界是平的
Pingback: CodeIgniter and Doctrine from scratch. | 世界是平的
Trackback: inspired
#75 by Richard on March 5th, 2012
| Quote
This is exactly what I was looking for thanks. I want to know how to create a search function in CI. It’s such a common feature in web applications but I haven’t seen many tutorials that go into much detail. Thanks again.
#76 by relationship quotes on February 10th, 2013
| Quote
Hi it’s me, I am also visiting this website daily, this site is really good and the viewers are actually sharing good thoughts.
#77 by Drusilla on April 24th, 2013
| Quote
Good replies in return of this matter with genuine arguments and
describing the whole thing regarding that.