Bu zor bir sorudur. Düşünebildiğim çözümler kokuyor ve daha sonra bazı sorunlara neden olabilir.
Patricus'un çalışmasını sağlamak için cevabını uzatacağım.
Patricus'un cevabı üzerine yorum yapacaktım ama açıklamak için çok fazla şey var. Onun çözümünü attach
ve sync
ile yapmak için bazı çirkin şeyler yapmalıyız.
Sorun
İlk önce onun çözümü ile sorunu tanımlamak edelim. Onun alıcıları ve ayarlayıcıları işe yarıyorlar, ancak otomToMany ilişkisi, sync
, attach
veya detach
'u çalıştırırken Pivot modelini kullanmaz. Bu, bunlardan birini aradığımızda her zaman $attributes
parametresi ile mutasyona uğramamış veri veritabanı sütununa konacaktır.
// This will skip the mutator on our extended Pivot class
$user->workspaces()->attach($workspace, ['role' => 'new role value']);
Biz sadece bunlardan birini çağırmak her zaman biz mutasyona uğramış verileri eklemek ve sadece mutasyonlu olmalıdır verilerle updateExistingPivot
çağırmak için ikinci bir parametre kullanamazsınız hatırlamak deneyebilirsiniz.Yani bir attach
Patricus belirtilen ne olurdu:
$user->workspaces()->attach($workspace);
$user->workspaces()->updateExistingPivot($workspaceId, ['role' => 'new role value']);
ve Pivot ilk örnekte görüldüğü attach
yöntemleri ikinci parametre olarak niteliklerini geçen doğru şekilde kullanabilirsiniz asla. Bu, daha fazla veritabanı ifadeleri ve kod çürümesi ile sonuçlanacaktır çünkü normal yolu yapmamanızı her zaman hatırlamanız gerekir. Her geliştiriciyi ya da kendinizin bile, amaçlanan ikinci parametreyle attach
yöntemini kullanmamayı bildiğinizi düşünüyorsanız, daha sonra ciddi sorunlarla karşılaşabilirsiniz.
Solution
bazı çılgın uzanan yapmalıdır Pivot sütunlarda mutator ile attach
arama yapabilmek için (denenmemiş ve kusurlu). Bunu test etmedim ama denemeyi düşünüyorsanız, doğru yolda olmanızı sağlayabilir.
use Illuminate\Database\Eloquent\Relations\BelongsToMany;
class UserWorkspaceBelongsToMany extends BelongsToMany {
public function attach($id, array $attributes = [], $touch = true)
{
$role = $attributes['role'];
unset($attributes['role']);
parent::attach($id, $attributes, $touch);
$this->updateExistingPivot($id, ['role' => $role], $touch);
}
// You will need sync here too
}
Şimdi her Model::belongsToMany
Normal BelongsToMany
yerine yeni UserWorkspaceBelongsToMany
sınıfını kullanın yapmak zorunda: Biz ilk BelongsToMany
uzanır ve özel attach
yöntemi uygular kendi ilişki sınıfı oluşturmak gerekir. Bizim Kullanıcı ve Çalışma Alanı sınıfında belongsToMany
alay bunu: Gördüğünüz gibi
// put this in the User and Workspace Class
public function userWorkspaceBelongsToMany($related, $table = null, $foreignKey = null, $otherKey = null, $relation = null)
{
if (is_null($relation)) {
$relation = $this->getBelongsToManyCaller();
}
$foreignKey = $foreignKey ?: $this->getForeignKey();
$instance = new $related;
$otherKey = $otherKey ?: $instance->getForeignKey();
if (is_null($table)) {
$table = $this->joiningTable($related);
}
$query = $instance->newQuery();
return new UserWorkspaceBelongsToMany($query, $this, $table, $foreignKey, $otherKey, $relation);
}
, hala veritabanı daha aradığınız ama biz Pivot özellikleri ile attach
çağıran birisi hakkında endişelenmenize gerek yoktur ve Mutasyona uğramıyorlar.
class User extends Model {
public function workspaces() {
return $this->userWorkspaceBelongsToMany('App\Models\Workspace')->withPivot('role');
}
}
class Workspace extends Model {
public function users() {
return $this->userWorkspaceBelongsToMany('App\Models\User')->withPivot('role');
}
}
ben elle yapmaya çalışıyorum:
Şimdi normal yerine belongsToMany senin modelleri içinde ki kullanırlar. İşte sahip olduğum şey: http://laravel.io/bin/RE2ze – ATLChris