We have moved our forum to GitHub Discussions. For questions about Phalcon v3/v4/v5 you can visit here and for Phalcon v6 here.

Cannot save a record using its relationship

Hello,

Given the following two very basic models:

class User extends \Phalcon\Mvc\Model {
    public $id;
    public $password;

    public function initialize() {
        $this->hasOne('id', 'Person', 'user_id', [
            'alias' => 'corresponding_person'
        ]);
    }
}
// CREATE TABLE User (
//   id int(10) NOT NULL AUTO_INCREMENT,
//   password VARCHAR(30),
//   PRIMARY KEY (id)
// );
class Person extends \Phalcon\Mvc\Model {
    public $id;
    public $user_id;
    public $name;

    public function initialize() {
        $this->hasOne('user_id', 'User', 'id', [
            'alias' => 'corresponding_user'
        ]);
    }
}
// CREATE TABLE Person (
//   id int(10) NOT NULL AUTO_INCREMENT,       
//   user_id int(10) NOT NULL,
//   name VARCHAR(30),
//   PRIMARY KEY (id)
// );

and this controller:

class IndexController extends ControllerBase {

    public function indexAction() {
        $User = new User();
        $User->password = 'secret';
        $User->save();

        $Person = new Person();
        $Person->name = 'John';
        $Person->corresponding_user = $User;

        if (! $Person->save()) {
            die(
                'Messages : ' . print_r($Person->getMessages(), true) . "\n" . 
                '$User->id : ' . $User->id
            );
        }
    }
}

When I run the controller, I get:

Messages : Array
(
    [0] => Phalcon\Mvc\Model\Message Object
        (
            [_type:protected] => PresenceOf
            [_message:protected] => user_id is required
            [_field:protected] => user_id
            [_model:protected] => 
            [_code:protected] => 0
        )
)
$User->id : 4

$User is saved, but not $Person.

It works if I use $Person->user_id = $User->id; but shouldn' it also work using the relationship defined in the model?

(Note: removing the relationship aliases and using $Person->User = $User produces the same error)

Thanks in advance for any help



8.1k
Accepted
answer
edited Jun '14

By chance I am currently also dealing with hasOne relationships (or 1:0..1 relationships to be more precise). Also having trouble getting stuff saved when specifiying the related model/record..

What happens if you change the hasOne in Person to belongsTo?



8.2k

Thank you renskii, it works. But then I'm confused: if I have to use belongsTo for 1-1 relationships, when am I supposed to use hasOne??? :-|



8.1k
edited Jun '14

@kofkof01 yes, I am also confused.. :) I was already planning on opening a topic on this, but it seems you kinda beat me to the punch ;)

The docs seem to explain belongsTo differently. Here: https://docs.phalcon.io/en/latest/reference/models.html#defining-relationships it sais: Defines a n-1 relationship

In the API reference https://docs.phalcon.io/en/latest/api/Phalcon\_Mvc\_Model.html there is: Setup a relation reverse 1-1 between two models

There's little info to be found on hasOne. So I am not really sure.. :)

edit: btw - if your relationship is 1:1, you can remove id from Person of course, and just use user_id as your PK (?) So I guess you can 'denote' 1 table as the 'master table' (having an auto-increment id), and add the belongsTo to the related 1:1?



22.8k
edited Jun '14

I usually think like that:

A Person has User

A User belongs to Person



8.2k
edited Jun '14

@sn0opr, I think it's the other way round. I've just found this in CakePHP doc:

The belongsTo association is a natural complement to the hasOne and hasMany associations: it allows us to see the data from the other direction.

[...]

If a model(table) contains a foreign key, it belongsTo the other model(table).

So if Phalcon works the same (and I bet it does), it seems a 1-1 relationship must be declared by using:

  • belongsTo() in the referencing model (the one with the foreign key)
  • hasOne() in the referenced model (the one the foreign key points to)

...which would explain why @renskii's solution works.



8.1k

@kofkof01 nice find. Seems plausible!