前提・実現したいこと
以下のような users, managers, staffs テーブルの構成で staffs テーブルにレコードを登録する際に、manager_id が managers テーブルに存在するかのチェックを行いたいです。
(構成はあくまで一例のため managers と staffs を別々に登録するなどは想定していません。)
テーブル構成と想定値
users
id | hoge | ...etc |
---|---|---|
1 | 123 | |
2 | 456 |
managers
user_id | huga | ...etc |
---|---|---|
1 | abc |
staffs
user_id | manager_id | piyo | ...etc |
---|---|---|---|
2 | 1 | あいう |
発生している問題・エラーメッセージ
トランザクションのコミット前に指定した id が managers テーブルに存在するかのチェックができない
該当のソースコード
※useしていないクラスや、未定義変数が急に出現していたりしますが、コードを簡略にするため一部コードを省略しています。
php
1 2class SampleClass 3{ 4 public function save() 5 { 6 try { 7 DB::beginTransaction(); 8 $managerId = $this->saveManager(/* users テーブルと managers テーブルに保存する処理。user_id が返却される */); 9 // ManagerId クラスのインスタンス化の際に managers.id として適切かのチェックをしたい 10 // DB::commit();の前なので必ず UnexpectedValueException が投げられてしまう 11 $this->saveStaff($values, new ManagerId($managerId)); 12 DB::commit(); 13 } catch (\Throwable $th) { 14 DB::rollback(); 15 // ... 処理 16 } 17 // ... 処理 18 } 19 20 protected function saveManager($args): string 21 { 22 $userId = User::insertGetId([/* users テーブルに保存する値 */]); 23 Manager::insert(['user_id' => $userId/* ...etc */]); 24 25 return $userId; 26 } 27 28 protected function saveStaff($values, ManagerId $id) 29 { 30 $userId = User::insertGetId([/* users テーブルに保存する値 */]); 31 Staff::insert(['user_id' => $userId, 'manager_id' => $id->getId()/* ...etc */]); 32 } 33} 34
ManagerId.php
php
1 2class ManagerId 3{ 4 private string $value; 5 6 public function __construct(string $value) 7 { 8 $this->value = $value; 9 10 if (!$this->exist()) { 11 throw new UnexpectedValueException('存在するマネージャーIDを指定してください。'); 12 } 13 } 14 15 public function getId(): string 16 { 17 return $this->value; 18 } 19 20 public function exist(): bool 21 { 22 return Manager::where('user_id', $this->value)->exists(); 23 } 24}
試したこと
managers テーブルに存在するかのチェックをやめる。
トランザクションを実施しないようにする。
[トランザクション コミット前 存在チェック] などで検索しましたが、該当記事が見つからないもしくは理解できないため解消できませんでした。
補足情報(FW/ツールのバージョンなど)
ツール | version |
---|---|
php | 7.4 |
Laravel | 8 |
MySQL | 5.7.34 |
トランザクションについてあまり詳しくないため、そもそも理論的にできないことをしているのかの判断もできていない状態です。
お手数ですがご指導いただけますと助かります。
回答2件
あなたの回答
tips
プレビュー