Deploy Ladill Care / deploy (push) Successful in 1m29s
Replace optional “All branches” with required branch checkboxes; doctors may switch only among assigned sites, never org-wide by default. Co-authored-by: Cursor <cursoragent@cursor.com>
78 lines
2.3 KiB
PHP
78 lines
2.3 KiB
PHP
<?php
|
|
|
|
namespace App\Http\Controllers\Care\Concerns;
|
|
|
|
use App\Models\Member;
|
|
use App\Models\Organization;
|
|
use App\Services\Care\CarePermissions;
|
|
use App\Services\Care\OrganizationResolver;
|
|
use Illuminate\Database\Eloquent\Builder;
|
|
use Illuminate\Database\Eloquent\Model;
|
|
use Illuminate\Http\Request;
|
|
|
|
trait ScopesToAccount
|
|
{
|
|
/**
|
|
* Tenant data owner — always the organization owner_ref.
|
|
* Staff members must read/write the employer's records, not their own public_id.
|
|
*/
|
|
protected function ownerRef(Request $request): string
|
|
{
|
|
return (string) $this->organization($request)->owner_ref;
|
|
}
|
|
|
|
/** Acting user (audit / created_by), distinct from the tenant owner. */
|
|
protected function actorRef(Request $request): string
|
|
{
|
|
return (string) $request->user()->public_id;
|
|
}
|
|
|
|
protected function organization(Request $request): Organization
|
|
{
|
|
$organization = $request->attributes->get('care.organization')
|
|
?? app(OrganizationResolver::class)->resolveForUser($request->user());
|
|
|
|
abort_unless($organization, 404);
|
|
|
|
return $organization;
|
|
}
|
|
|
|
protected function member(Request $request): ?Member
|
|
{
|
|
return $request->attributes->get('care.member')
|
|
?? app(OrganizationResolver::class)->memberFor($request->user(), $this->organization($request));
|
|
}
|
|
|
|
protected function authorizeAbility(Request $request, string $ability): void
|
|
{
|
|
abort_unless(
|
|
app(CarePermissions::class)->can($this->member($request), $ability),
|
|
403,
|
|
);
|
|
}
|
|
|
|
protected function authorizeOwner(Request $request, Model $model): void
|
|
{
|
|
abort_unless($model->getAttribute('owner_ref') === $this->ownerRef($request), 404);
|
|
}
|
|
|
|
protected function scopeToBranch(Request $request, Builder $query, string $column = 'branch_id'): Builder
|
|
{
|
|
$allowed = app(OrganizationResolver::class)->allowedBranchIds($this->member($request));
|
|
|
|
if ($allowed !== null) {
|
|
$query->whereIn($column, $allowed !== [] ? $allowed : [0]);
|
|
}
|
|
|
|
return $query;
|
|
}
|
|
|
|
protected function authorizeBranch(Request $request, ?int $branchId): void
|
|
{
|
|
abort_unless(
|
|
app(OrganizationResolver::class)->mayAccessBranch($this->member($request), $branchId),
|
|
404,
|
|
);
|
|
}
|
|
}
|