kohanakohana-3kohana-ormkohana-3.2kohana-db

Kohana - Validate ORM


I'm using Kohana for some time now. I'm using "has_many", "has_one", "belongs_to" without a problem, my question is:

If I have 2 tables like this:

tbl_foo1

id | tbl_foo2_id | field1
-------------------------
1  | 2           | bar
2  | 1           | foo

tbl_foo2

id | field1
-----------
1  | foo
2  | bar

I have to have a relation like: tbl_foo1 belongs to tbl_foo2 and tbl_foo2 has many tbl_foo1 So far so good.

The problem is when I try to save the relation in the controller.. So I have this code:

$t1 = ORM::factory('tbl_foo1')->values($values, $expected)->create();
$t2 = ORM::factory('tbl_foo2', $_POST['id']);
$t1->tbl_foo2_id = $t2;
$t1->save();

Ok, this should work, but I think this is not the best solution neither the most beautiful. For 2 reasons, 1 because of performance - it does 3 queries (1 to save $t1, 2 to find $t2, 3 to save relations of $t2 with $t1) and 2 because it may save empty records, because it doesn't validate the existence of the records in $t2.

So my main questions is, how this should be done?


My own solution

I used the solution that biakaveron gave me, thank you. But still, there was the validation problem.. so I spent some time and came up with a solution, using the same example:

$t2 = ORM::factory('tbl_foo2', $_POST['id']);
$t1 = ORM::factory('tbl_foo1')->values($values, $expected);
$t1->foo2 = $t2; // foo2 is a belongs_to relationship
$t1->create();

in the tbl_foo1 model I added the rules function:

public function rules()
{
    'foo2_id' => array('not_empty')
}

So this way, I don't have to do another query, which is good for performance and it's a simple way to do it. And it works, because, when the ORM tries to find the id of the model tbl_foo2, if it doesn't find it, it returns NULL, so it will always empty no matter what!

Note: I used the DB transactions too (because this is just a portion of the process), so if one of the queries breaks for some reason, well no query will run. Just remember, you have to use one database engine that supports transactions (mine is InnoDB).


Solution

  • 1 You can save model with belongs_to object:

    $t2 = ORM::factory('tbl_foo2', $this->request->post('id'));
    if (!$t2->loaded()) 
    {
        // wrong ID for tbl_foo2
    }
    
    $t1 = ORM::factory('tbl_foo1')->values($values, $expected);
    $t1->foo2 = $t2; // foo2 is a belongs_to relationship
    $t1->create();
    

    2 Check tbl_foo2_id with special callback.