You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Laravel中基于用户角色实现页面内容隐藏及权限控制

Laravel原生角色权限控制实现方案(无第三方依赖)

1. 角色基础表结构搭建

不需要复杂的多表关联,单字段即可满足你当前5类角色的需求,后续要扩展精细权限再加中间表即可:

  • 给users表新增role字段,类型设为string,存储角色标识,比如admin/doctor/patient/assistant/laboratorian,默认值可设为patient
  • 迁移文件示例:
Schema::table('users', function (Blueprint $table) {
    $table->string('role')->default('patient');
});
  • 在User模型中统一管理角色常量,加快捷角色判断方法,避免硬编码:
// app/Models/User.php
class User extends Authenticatable
{
    const ROLE_ADMIN = 'admin';
    const ROLE_DOCTOR = 'doctor';
    const ROLE_PATIENT = 'patient';
    const ROLE_ASSISTANT = 'assistant';
    const ROLE_LABORATORIAN = 'laboratorian';

    // 快捷判断角色
    public function hasRole(string $role): bool
    {
        return $this->role === $role;
    }
}

2. 用Gates定义全局通用权限

Gates适合定义和特定模型无关的全局权限,比如菜单访问、页面公共区域显隐控制:

  • 在app/Providers/AuthServiceProvider.php的boot方法中注册Gates:
public function boot()
{
    $this->registerPolicies();

    // 示例:定义患者管理菜单的访问权限:仅管理员、医生、助手可访问
    Gate::define('access-patient-menu', function (User $user) {
        return in_array($user->role, [
            User::ROLE_ADMIN,
            User::ROLE_DOCTOR,
            User::ROLE_ASSISTANT
        ]);
    });

    // 示例:定义检验报告查看权限:管理员、医生、检验人员、报告所属患者可查看
    Gate::define('view-lab-report', function (User $user, Report $report) {
        return $user->hasRole(User::ROLE_ADMIN)
            || $user->hasRole(User::ROLE_DOCTOR)
            || $user->hasRole(User::ROLE_LABORATORIAN)
            || $user->id === $report->patient_id;
    });
}

3. 用Policy定义模型级操作权限

Policy专门绑定特定模型的操作权限,你要求的患者信息编辑、删除权限就用Policy实现:

  • 生成绑定Patient模型的Policy,执行命令:php artisan make:policy PatientPolicy --model=Patient
  • 编辑app/Policies/PatientPolicy.php的对应方法:
// 患者信息编辑权限:管理员、负责该患者的医生、对应医生的助手可编辑
public function update(User $user, Patient $patient): bool
{
    return $user->hasRole(User::ROLE_ADMIN)
        || ($user->hasRole(User::ROLE_DOCTOR) && $user->id === $patient->doctor_id)
        || ($user->hasRole(User::ROLE_ASSISTANT) && $user->doctor_id === $patient->doctor_id);
}

// 患者信息删除权限:仅管理员可删除
public function delete(User $user, Patient $patient): bool
{
    return $user->hasRole(User::ROLE_ADMIN);
}
  • 必须在AuthServiceProvider的$policies数组中绑定模型和Policy才能生效:
protected $policies = [
    Patient::class => PatientPolicy::class,
];

4. 不同场景的权限调用方式

后端控制器/接口调用

  • 控制器方法中直接用authorize校验,无权限会自动抛出403异常:
public function update(Request $request, Patient $patient)
{
    $this->authorize('update', $patient);
    // 后续业务逻辑
}
  • 全局Gates权限校验用Gate门面:
if (Gate::allows('access-patient-menu')) {
    // 对应业务逻辑
}

Blade视图显隐控制

  • 用@can指令控制菜单、按钮、页面局部的显示隐藏:
{{-- 患者管理菜单仅有权限用户可见 --}}
@can('access-patient-menu')
    <li><a href="{{ route('patients.index') }}">患者管理</a></li>
@endcan

{{-- 编辑按钮仅拥有患者编辑权限的用户可见 --}}
@can('update', $patient)
    <button>编辑患者信息</button>
@endcan
  • 反向控制隐藏用@cannot指令即可。

内容的提问来源于stack exchange,提问作者Shady Hesham

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.04 15:42:01