17

Doctrine-Entity に人間が読める ID を実装したいと思います。「PRE12-00005」のようなものを機能させて追加するためにDB-IDを保持したい(接頭辞と年で、毎年0から始まる)。Custom-ID-Generator を追加しようとしましたが、Doctrine は 1 つのエンティティで 2 つの生成された値を処理できないようです。

/**
 * @var integer
 * @ORM\Column(name="id", type="integer")
 * @ORM\Id
 * @ORM\GeneratedValue(strategy="IDENTITY")
 */
protected $id;

/**
 * @var string
 * @ORM\Column(name="name", type="string", length=25, unique=true)
 * @ORM\GeneratedValue(strategy="CUSTOM")
 * @ORM\CustomIdGenerator(class="NameGenerator")
 */
protected $name;

Doctrine は常にジェネレーターからの戻り値を「id」フィールドに保存し、null を「name」に保存しようとします。それを実装する別の方法はありますか?

4

1 に答える 1

20

私が知っていることから、GeneratedValue 戦略は主キー用に予約されています。つまり、エンティティごとに 1 回しか使用できません。

ただし、ニーズに応じていくつかのオプションがあります。

  • 初めて永続化する前に、名前に好きな値を設定して、いつでもprePersist ライフサイクル イベントを作成できます。

  • id に依存して別の一意の id を生成する場合は、postPersist イベントを実装し、そこに名前を設定して、2 回フラッシュするようにすることができます (1 回目は主キーを生成し、2 回目は名前を保存します)。

  • データベースで名前がしばらくの間空であっても問題ない場合は、postLoad イベントを実装しても問題ない可能性があります。このイベントは、空の場合に名前を埋めます。このようにして、アプリケーションは常に名前を認識し (名前はデータベースからロードされるか、postLoad イベントによって入力されるため)、最初の保存後に初めて情報を追加または編集するときに、名前も保存されます。

  • 名前を保存せずに、いくつかの cronjob/deamon/queue によって生成されても問題ない可能性があるため、アプリケーションはそれを処理する必要がありません。あなたがする必要がある唯一のことは、欠落している名前が何かを台無しにしないことを確認することです.

  • おそらく、主キーに依存せず、したがってグローバル イベント ハンドラによって生成できるキーを生成しても問題ないかもしれません。もちろん、そのようなイベント ハンドラーはグローバルであるため、正しいエンティティであるかどうかに関係なく、永続化するすべてのオブジェクトに対して呼び出されるという欠点があります。

  • 最後に、データベースにこれを処理させるために、ストアド プロシージャ/トリガーにフォールバックしても問題ない場合があります。このようにして、アプリケーション内でこれを台無しにする必要はありません。ただし、途中で落とし穴があるかもしれないことに注意してください (コードではなくデータベースにあるため、開発者がこれを忘れるなど)。

他の方法があるかもしれません。私が言おうとしていたのは、主キー以外のプロパティに generatedValue を使用しないでください!

于 2012-12-17T15:44:42.810 に答える