[英]Simplifying database relationships design
我有這個Laravel小項目,成員可以付費參加課程,支付保險,參加活動或付費以通過特殊類型的考試。
因此,我有5個表members
, classes
, insurance
, events
和exams
,並且我需要添加payments
表,以便可以跟蹤每個表中的members成員。
因此,目前payments
表將如下所示:
id date amount member_id class_id insurance_id event_id exam_id
1 2019-01-01 150 2 1 NULL NULL NULL
2 2019-01-01 250 11 NULL 14 NULL NULL
3 2019-01-01 220 15 NULL NULL 6 NULL
4 2019-01-01 350 32 NULL NULL NULL 8
在沒有付款表中的class_id, insurance_id, event_id, exam_id
字段的情況下,有沒有一種更好的方法,因為這會使關系變得更復雜,我猜想也可能只是使用Laravel作為PHP框架進行數據庫查詢。
在一個表中不使用所有ID的情況下,請使用事務表,並在所有這些表中使用該transaction_id。
表交易=> id,payment_data,created_at,created_by等
表事件=> id,名稱,transaction_id等
我認為最好的方法是一對多的多態關系。
為此,您需要:
members
表,用於保存成員數據。 classes
, insurance
, events
和exams
) payments
表: Schema::create('payments', function (Blueprint $table) {
$table->increments('id');
// Payment related fields like date and amount
$table->unsignedInteger('member_id');
// Assuming id is the primary key on the members table
$table->foreign('member_id')->references('id')->on('members');
// This one will create two fields:
// - payable_type
// - payable_id
$table->morphs('payable');
});
這樣,每條記錄將包含進行付款的成員(通過member_id
)和付費實體(通過payable_type
和payable_id
)。
然后,您必須在付款模型上設置變體關系,例如:
// app\Payment.php
class Payment extends Model
{
// ...
public function payable()
{
return $this->morphTo();
}
public function member()
{
return $this->belongsTo(Member::class);
}
}
您的會員模型為:
// app\Member.php
class Member extends Model
{
// ...
public function payments()
{
return $this->hasMany(Payment::class);
}
}
對於每個應付款實體:
// app\Insurance.php
class Insurance extends Model
{
// ...
public function payments()
{
return $this->morphMany(Payment::class, 'payable');
}
}
// app\Event.php
class Event extends Model
{
// ...
public function payments()
{
return $this->morphMany(Payment::class, 'payable');
}
}
// app\Exam.php
class Exam extends Model
{
// ...
public function payments()
{
return $this->morphMany(Payment::class, 'payable');
}
}
// app\Course.php
// I renamed "Class" payable entity to "Course"
// as "class" is a reserved keyword in PHP and
// you can't give a class the name "Class".
class Course extends Model
{
// ...
public function payments()
{
return $this->morphMany(Payment::class, 'payable');
}
}
如果您需要檢索用戶支付的所有付款(不同類型),則只需查詢成員模型,如下所示:
$member = Member::with('payments.payable')->first();
dd($member->payments);
如果您相應地設置模型關系,Laravel將基於具有匹配member_id的每個記錄的payable_type和payable_id解析不同的正確Eloquent模型實例。
結果, $member->payments
將是Payment實例的集合,每個實例與Insurance
, Exam
, Course
和Event
類之一相關(基於存儲在數據庫中的payable_type)。
作為參考和更詳細的用法,您可以在此處查看Laravel的官方文檔。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.