Closed iamsayantan closed 5 years ago
Hi, iamsayantan.
We needed something like this. We did override Rinvex\Attributes\Models\Attribute
model and added morphTo relationship
use Rinvex\Attributes\Models\Attribute as RinvexAttribute;
class Attribute extends RinvexAttribute {
...
// Make sure to create migration where you add morph fields into attributes table
public function owner()
{
return $this->morphTo('owner');
}
}
And than in your repository (or model as local scope) you can create methods where you are filtering by owner, what in your case can be company.
// Somewhere in repository
public function findOwned($models = [])
{
$attributes = $this->model;
if (!is_array($models)) {
$models = [$models];
}
foreach ($models as $key => $model) {
if ($key == 0) {
$attributes = $attributes->where(function ($subquery) use ($model) {
$subquery->where('owner_type', get_class($model))
->where('owner_id', $model->id)
;
});
} else {
$attributes = $attributes->orWhere(function ($subquery) use ($model) {
$subquery->where('owner_type', get_class($model))
->where('owner_id', $model->id)
;
});
}
}
return $attributes;
}
And then search company attributes with:
$company_attrs = $this->attributesRepository->findOwned($company)
For branches you can use default package entities.
I hope this will help.
Your solution looks good. We achieved this by adding company_id
in attribute_entity
table and overrode Rinvex\Attributes\Models\AttributeEntity
to add global CompanyScope
.
<?php
namespace App\EAVModels;
use App\Scopes\CompanyScope;
use Rinvex\Attributes\Models\AttributeEntity as BaseAttributeEntity;
class AttributeEntity extends BaseAttributeEntity
{
protected $fillable = [
'entity_type',
'company_id'
];
/**
* The CompanyScope global scope makes sure that all the custom attributes are company
* specific.
*/
protected static function boot()
{
parent::boot();
static::addGlobalScope(new CompanyScope);
}
}
And then overrode Rinvex\Attributes\Models\Attribute
to add a mutator which updates the company_id
field in attribute_entity
table.
<?php
namespace App\EAVModels;
use Rinvex\Attributes\Models\Attribute as BaseAttribute;
class Attribute extends BaseAttribute
{
protected $fillable = [
'name',
'slug',
'description',
'sort_order',
'group',
'type',
'is_required',
'is_collection',
'default',
'entities',
'company_id'
];
/**
* This mutator sets the company id to the attribute_entity table.
*
* @param $companyId
*/
public function setCompanyIdAttribute($companyId): void
{
static::saved(function ($model) use ($companyId) {
$this->entities()->withoutGlobalScopes()->update(['company_id' => $companyId]);
});
}
}
Nice discussion! I'm curious, do you use specific tenantable package, or custom built solution? You may want to consider also utilizing rinvex/laravel-tenants
also 🙂
Hi, first of all thank you for this awesome work. However our requirements are little different. We are working on a multi tenant application and I was wondering if it is possible to make the custom attribute tenant specific. To give an idea, in our case, a
Company
is a tenant. ACompany
can have multipleBranch
es. EachCompany
can set up custom attributes for theirBranch
es which should be available only to that company. So will it be possible to have this kind of control with the current project? Any help is welcome. Thank you!