Doctrine and composite unique keys

PhpMysqlDoctrine Orm

Php Problem Overview


I want to do composite unique key in doctrine. Those are my fields:

/**
 * @var string $videoDimension
 *
 * @Column(name="video_dimension", type="string", nullable=false)
 */
private $videoDimension;

/**
 * @var string $videoBitrate
 *
 * @Column(name="video_bitrate", type="string", nullable=false)
 */
private $videoBitrate;

How can I show doctrine, that those combined together are composite unique key?

Php Solutions


Solution 1 - Php

Answer the question:

use Doctrine\ORM\Mapping\UniqueConstraint;

/**
 * Common\Model\Entity\VideoSettings
 *
 * @Table(name="video_settings", 
 *    uniqueConstraints={
 *        @UniqueConstraint(name="video_unique", 
 *            columns={"video_dimension", "video_bitrate"})
 *    }
 * )
 * @Entity
 */

See @UniqueConstraint

Solution 2 - Php

I find it more verbose to use only ORM and then prefix ORM in annotations. Also note that you can break annotation to several lines to make it more readable especially if you have several items to mention (index in the example below).

use Doctrine\ORM\Mapping as ORM;

/**
 * VideoSettings
 *
 * @ORM\Cache(usage="NONSTRICT_READ_WRITE")
 * @ORM\Entity(repositoryClass="AppBundle\Repository\VideoSettingsRepository")
 * @ORM\Table(name="emails", uniqueConstraints={
 *      @ORM\UniqueConstraint(name="dimension_bitrate", columns={"video_dimension", "video_bitrate"})
 * }, indexes={
 *      @ORM\Index(name="name", columns={"name"})
 * })
 */
class VideoSettings

Solution 3 - Php

In case someone want use PHP 8 Attributes instead of Doctrine annotations:

use Doctrine\ORM\Mapping as ORM;

#[ORM\Entity]
#[ORM\UniqueConstraint(
  name: 'video_unique_idx',
  columns: ['video_dimension', 'video_bitrate']
)]

Solution 4 - Php

I know this is an old question, but I came across it while looking for a way to create composite PK and thought it could use some update.

Things are actually much simpler if what you need is a Composite Primary Key. (Which, of course, guarantees uniqueness) Doctrine documentation contains some nice examples by this url: http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/tutorials/composite-primary-keys.html

So the original example could look something like this:

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

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

A few notes here:

  1. Column "name" is omitted since Doctrine is able to guess it based on the property name
  2. Since videoDimension and videoBitrate are both parts of the PK - there is no need to specify nullable = false
  3. If required - the Composite PK may be composed of foreign keys, so feel free to add some relational mappings

Solution 5 - Php

XML version :

<unique-constraints>
    <unique-constraint columns="column1,column2" name="give_some_explicit_name" />
</unique-constraints>

More details in the docs :
https://www.doctrine-project.org/projects/doctrine-orm/en/2.7/reference/xml-mapping.html#defining-indexes-or-unique-constraints

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionNikooleView Question on Stackoverflow
Solution 1 - PhpNikooleView Answer on Stackoverflow
Solution 2 - PhpluchaninovView Answer on Stackoverflow
Solution 3 - PhpAz.YounessView Answer on Stackoverflow
Solution 4 - PhpStas ParshinView Answer on Stackoverflow
Solution 5 - PhpBalmipourView Answer on Stackoverflow