phalcon / cphalcon

High performance, full-stack PHP framework delivered as a C extension.
https://phalcon.io
BSD 3-Clause "New" or "Revised" License
10.79k stars 1.96k forks source link

[BUG]: Problem with saving null value on related entities. #16611

Open markofo opened 5 months ago

markofo commented 5 months ago

Problem description

If we try to set related entities to null and then call save on the entity, everything seems fine. If we call the getter before setting the value to null, the related entity is still set to the original value and the SQL update is not performed. In Phalcon 3, this way of saving worked.

How to reproduce

Database structure:

CREATE TABLE payment_notices (
    id serial4 NOT NULL,
    id_payment int4 NULL,
    CONSTRAINT payment_notices_pkey PRIMARY KEY (id)
);

CREATE TABLE payments (
    id serial4 NOT NULL,
    number varchar(255),
    CONSTRAINT payments_pkey PRIMARY KEY (id)
);

ALTER TABLE payment_notices ADD CONSTRAINT "fk.payment_notices.id_payment" FOREIGN KEY (id_payment) REFERENCES payments(id) ON DELETE SET NULL;

Payment class has a defined relationship:

$this->hasMany('id', PaymentNotice::class, 'idPayment', [
    'alias' => 'paymentNotices'
]);

Payment notice class has a defined relationship:

$this->belongsTo('idPayment', Payment::class, 'id',[
    'alias' => 'payment'
]);

And a setter:

public function setPayment(Payment $payment = null): PaymentNotice {
    $this->payment = $payment;
    if ($payment == null) {
        $this->idPayment = null;
    }
    return $this;
}

In the application, we set payment to null and save Payment notice:

This is working:

$paymentNotice = PaymentNotice::findFirst(1);
$paymentNotice->setPayment(null);
$paymentNotice->save(); // in this case null value will be saved

This is not working:

$paymentNotice = PaymentNotice::findFirst(1);
$payment = $paymentNotice->getPayment(); // calling getter causes the null value not to be saved on the relatied entity
$paymentNotice->setPayment(null);
$paymentNotice->save();

Environment Version: Phalcon 5.7 PHP: 8.2