Cannot be null error when foreign key is last property #6249

Closed
opened 2026-01-22 15:29:32 +01:00 by admin · 1 comment
Owner

Originally created by @manseuk on GitHub (Jun 7, 2019).

Originally assigned to: @Ocramius on GitHub.

Bug Report

Q A
BC Break no
Version 2.6.3

Summary

When using an entity with a composite key and another entity with a foreign key associated with the composite primary key, if the foreign key is set to NULL and its the last property then an error is encountered

Current behavior

  An exception occurred while executing 'INSERT INTO review (id, title, tenant_id, user_id, page_id) VALUES (?, ?, ?, ?, ?)' with params ["daff1110-80ba-4caa-8ea8-1f2c18a03f8c", "Title 2", null, "45e061f6-12cd-4ada-86cb-c3fb81fb613a", null]:

  SQLSTATE[23000]: Integrity constraint violation: 1048 Column 'tenant_id' cannot be null

How to reproduce

Create the following entities
Tenant.php

/**
 * @ORM\Entity()
 * @ORM\Table(name="tenant")
 */
class Tenant
{
    /**
     * @var UuidInterface
     *
     * @ORM\Id()
     * @ORM\Column(type="uuid")
     */
    private $id;

    /**
     * @var string
     *
     * @ORM\Column(type="string")
     */
    private $name;
}

User.php

/**
 * @ORM\Entity()
 * @ORM\Table(name="user")
 */
class User
{

    /**
     * @var UuidInterface
     *
     * @ORM\Id()
     * @ORM\Column(type="uuid")
     */
    private $id;

    /**
     * @var Tenant
     *
     * @ORM\Id()
     * @ORM\ManyToOne(targetEntity="Tenant")
     */
    private $tenant;
}

Page.php

/**
 * @ORM\Entity()
 * @ORM\Table(name="page")
 */
class Page
{

    /**
     * @var UuidInterface
     *
     * @ORM\Id()
     * @ORM\Column(type="uuid")
     */
    private $id;

    /**
     * @var Tenant
     *
     * @ORM\Id()
     * @ORM\ManyToOne(targetEntity="Tenant")
     */
    private $tenant;

    /**
     * @var string
     *
     * @ORM\Column(type="string")
     */
    private $title;

    /**
     * Id of the rate plan the zone is for
     *
     * @var User
     *
     * @ORM\ManyToOne(targetEntity="User")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="user_id", referencedColumnName="id"),
     *   @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id")
     * })
     */
    private $user;
}

Review.php

/**
 * @ORM\Entity()
 * @ORM\Table(name="review")
 */
class Review
{

    /**
     * @var UuidInterface
     *
     * @ORM\Id()
     * @ORM\Column(type="uuid")
     */
    private $id;

    /**
     * @var Tenant
     *
     * @ORM\Id()
     * @ORM\ManyToOne(targetEntity="Tenant")
     */
    private $tenant;

    /**
     * @var string
     *
     * @ORM\Column(type="string")
     */
    private $title;

    /**
     * @var User
     *
     * @ORM\ManyToOne(targetEntity="User")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="user_id", referencedColumnName="id"),
     *   @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id")
     * })
     */
    private $user;

    /**
     * @var Page
     *
     * @ORM\ManyToOne(targetEntity="Page")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="page_id", referencedColumnName="id"),
     *   @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id")
     * })
     */
    private $page;
}

TestCommand.php

 $tenant = new Tenant();
        $tenant->setName('Test');
        $this->entityManager->persist($tenant);

        $user = new User();
        $user->setTenant($tenant);
        $user->setUsername('username');
        $this->entityManager->persist($user);

        $page = new Page();
        $page->setTenant($tenant);
        $page->setUser($user);
        $page->setTitle('Title');
        $this->entityManager->persist($page);

        $review = new Review();
        $review->setTenant($tenant);
        $review->setPage($page);
        $review->setTitle('Title');
        $this->entityManager->persist($review);

        $review2 = new Review();
        $review2->setTenant($tenant);
        $review2->setUser($user);
        $review2->setTitle('Title 2');
        $this->entityManager->persist($review2);
        $this->entityManager->flush();

Running the command TestCommand produces the following error

 An exception occurred while executing 'INSERT INTO review (id, title, tenant_id, user_id, page_id) VALUES (?, ?, ?, ?, ?)' with params ["daff1110-80ba-4caa-8ea8-1f2c18a03f8c", "Title 2", null, "45e061f6-12cd-4ada-86cb-c3fb81fb613a", null]:

  SQLSTATE[23000]: Integrity constraint violation: 1048 Column 'tenant_id' cannot be null

Updating the Review.php entity and moving the $tenant property to be last, like this

/**
 * @ORM\Entity()
 * @ORM\Table(name="review")
 */
class Review
{

    /**
     * @var UuidInterface
     *
     * @ORM\Id()
     * @ORM\Column(type="uuid")
     */
    private $id;
    
    /**
     * @var string
     *
     * @ORM\Column(type="string")
     */
    private $title;

    /**
     * @var User
     *
     * @ORM\ManyToOne(targetEntity="User")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="user_id", referencedColumnName="id"),
     *   @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id")
     * })
     */
    private $user;

    /**
     * @var Page
     *
     * @ORM\ManyToOne(targetEntity="Page")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="page_id", referencedColumnName="id"),
     *   @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id")
     * })
     */
    private $page;

    /**
     * @var Tenant
     *
     * @ORM\Id()
     * @ORM\ManyToOne(targetEntity="Tenant")
     */
    private $tenant;
}

and then executing the same command fixes the issue

I have attached the project, running composer install then bin/console test:test-command in its current state produces the error

Expected behavior

Command should execute successfully with the properties in the Review entity in any order
entitytest.zip

Originally created by @manseuk on GitHub (Jun 7, 2019). Originally assigned to: @Ocramius on GitHub. ### Bug Report <!-- Fill in the relevant information below to help triage your issue. --> | Q | A |------------ | ------ | BC Break | no | Version | 2.6.3 #### Summary When using an entity with a composite key and another entity with a foreign key associated with the composite primary key, if the foreign key is set to NULL and its the last property then an error is encountered #### Current behavior ``` An exception occurred while executing 'INSERT INTO review (id, title, tenant_id, user_id, page_id) VALUES (?, ?, ?, ?, ?)' with params ["daff1110-80ba-4caa-8ea8-1f2c18a03f8c", "Title 2", null, "45e061f6-12cd-4ada-86cb-c3fb81fb613a", null]: SQLSTATE[23000]: Integrity constraint violation: 1048 Column 'tenant_id' cannot be null ``` #### How to reproduce Create the following entities Tenant.php ``` /** * @ORM\Entity() * @ORM\Table(name="tenant") */ class Tenant { /** * @var UuidInterface * * @ORM\Id() * @ORM\Column(type="uuid") */ private $id; /** * @var string * * @ORM\Column(type="string") */ private $name; } ``` User.php ``` /** * @ORM\Entity() * @ORM\Table(name="user") */ class User { /** * @var UuidInterface * * @ORM\Id() * @ORM\Column(type="uuid") */ private $id; /** * @var Tenant * * @ORM\Id() * @ORM\ManyToOne(targetEntity="Tenant") */ private $tenant; } ``` Page.php ``` /** * @ORM\Entity() * @ORM\Table(name="page") */ class Page { /** * @var UuidInterface * * @ORM\Id() * @ORM\Column(type="uuid") */ private $id; /** * @var Tenant * * @ORM\Id() * @ORM\ManyToOne(targetEntity="Tenant") */ private $tenant; /** * @var string * * @ORM\Column(type="string") */ private $title; /** * Id of the rate plan the zone is for * * @var User * * @ORM\ManyToOne(targetEntity="User") * @ORM\JoinColumns({ * @ORM\JoinColumn(name="user_id", referencedColumnName="id"), * @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id") * }) */ private $user; } ``` Review.php ``` /** * @ORM\Entity() * @ORM\Table(name="review") */ class Review { /** * @var UuidInterface * * @ORM\Id() * @ORM\Column(type="uuid") */ private $id; /** * @var Tenant * * @ORM\Id() * @ORM\ManyToOne(targetEntity="Tenant") */ private $tenant; /** * @var string * * @ORM\Column(type="string") */ private $title; /** * @var User * * @ORM\ManyToOne(targetEntity="User") * @ORM\JoinColumns({ * @ORM\JoinColumn(name="user_id", referencedColumnName="id"), * @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id") * }) */ private $user; /** * @var Page * * @ORM\ManyToOne(targetEntity="Page") * @ORM\JoinColumns({ * @ORM\JoinColumn(name="page_id", referencedColumnName="id"), * @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id") * }) */ private $page; } ``` TestCommand.php ``` $tenant = new Tenant(); $tenant->setName('Test'); $this->entityManager->persist($tenant); $user = new User(); $user->setTenant($tenant); $user->setUsername('username'); $this->entityManager->persist($user); $page = new Page(); $page->setTenant($tenant); $page->setUser($user); $page->setTitle('Title'); $this->entityManager->persist($page); $review = new Review(); $review->setTenant($tenant); $review->setPage($page); $review->setTitle('Title'); $this->entityManager->persist($review); $review2 = new Review(); $review2->setTenant($tenant); $review2->setUser($user); $review2->setTitle('Title 2'); $this->entityManager->persist($review2); $this->entityManager->flush(); ``` Running the command `TestCommand` produces the following error ``` An exception occurred while executing 'INSERT INTO review (id, title, tenant_id, user_id, page_id) VALUES (?, ?, ?, ?, ?)' with params ["daff1110-80ba-4caa-8ea8-1f2c18a03f8c", "Title 2", null, "45e061f6-12cd-4ada-86cb-c3fb81fb613a", null]: SQLSTATE[23000]: Integrity constraint violation: 1048 Column 'tenant_id' cannot be null ``` Updating the `Review.php` entity and moving the `$tenant` property to be last, like this ``` /** * @ORM\Entity() * @ORM\Table(name="review") */ class Review { /** * @var UuidInterface * * @ORM\Id() * @ORM\Column(type="uuid") */ private $id; /** * @var string * * @ORM\Column(type="string") */ private $title; /** * @var User * * @ORM\ManyToOne(targetEntity="User") * @ORM\JoinColumns({ * @ORM\JoinColumn(name="user_id", referencedColumnName="id"), * @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id") * }) */ private $user; /** * @var Page * * @ORM\ManyToOne(targetEntity="Page") * @ORM\JoinColumns({ * @ORM\JoinColumn(name="page_id", referencedColumnName="id"), * @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id") * }) */ private $page; /** * @var Tenant * * @ORM\Id() * @ORM\ManyToOne(targetEntity="Tenant") */ private $tenant; } ``` and then executing the same command fixes the issue I have attached the project, running `composer install` then `bin/console test:test-command` in its current state produces the error #### Expected behavior Command should execute successfully with the properties in the Review entity in any order [entitytest.zip](https://github.com/doctrine/orm/files/3266073/entitytest.zip)
admin added the Invalid label 2026-01-22 15:29:32 +01:00
admin closed this issue 2026-01-22 15:29:33 +01:00
Author
Owner

@Ocramius commented on GitHub (Jun 10, 2019):

Your mappings are not valid. Specifically:


    /**
     * @ORM\ManyToOne(targetEntity="Tenant")
     */
    private $tenant;

// ... snip ...

    /**
     * @ORM\ManyToOne(targetEntity="User")
     * @ORM\JoinColumns({
     *   @ORM\JoinColumn(name="user_id", referencedColumnName="id"),
     *   @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id")
     * })
     */
    private $user;

You are re-using the tenant_id column for multiple associations, and that is not something the ORM supports.

You will need separate JoinColumn definitions for these two associations.

@Ocramius commented on GitHub (Jun 10, 2019): Your mappings are not valid. Specifically: ```php /** * @ORM\ManyToOne(targetEntity="Tenant") */ private $tenant; // ... snip ... /** * @ORM\ManyToOne(targetEntity="User") * @ORM\JoinColumns({ * @ORM\JoinColumn(name="user_id", referencedColumnName="id"), * @ORM\JoinColumn(name="tenant_id", referencedColumnName="tenant_id") * }) */ private $user; ``` You are re-using the `tenant_id` column for multiple associations, and that is not something the ORM supports. You will need separate `JoinColumn` definitions for these two associations.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: doctrine/archived-orm#6249