manoyeche/imachable

Imachable - 使用提供给用户的访问列表来为控制器方法添加保护,而不是使用路由。

v0.0.12 2021-03-09 04:01 UTC

This package is auto-updated.

Last update: 2024-09-09 04:23:55 UTC


README

使用用户提供的动态访问列表,而不是路由来为控制器方法添加保护。

安装

Composer

    composer require manoyeche/imaccessible

配置

用户模型

将Imachable特质添加到用户模型中

    use Imaccessible\Traits\Imaccessible;

    class User extends Authenticatable
    {
        use Imaccessible;

    .....

现在您可以使用 access_names 属性和 accessibles() hasMany 关系到您的用户模型。

    auth()->user()->access_names;

    .....

    User::find($id)->access_names;

    .....

    $user = User::find($id);

    $user->createAccess('USER_EDIT');

    .....

    $user->revokeAccess('USER_EDIT');

UserAccessible 迁移

使用数据库表动态更改访问名称。

    php artisan vendor:publish --provider="Imaccessible\Providers\ImaccessibleServiceProvider" --tag="migrations"

    php artisan migrate
    use Imaccessible\Models\UserAccessible;

    .....

    UserAccessible::create([
        'user_id' => $user_id,
        'name' => 'USER_EDIT'
    ]);

保护控制器方法

中间件

向您的中间件添加条件。

    use Imaccessible\Imaccessible;

    class AuthMember
    {

        public function handle(Request $request, Closure $next)
        {
            // if (!auth()->check()) {
            //     return redirect()->route('login');
            // }

            if (!Imaccessible::verifyAccess(auth()->user()->access_names)) {
                abort(404);
            }

            return $next($request);
        }
    .....

控制器

创建一个静态函数 accessRules(),它返回一个访问名称数组。当中间件根据路由中的当前操作验证访问时调用这些函数。

    public function __construct()
    {
        $this->middleware([
            'authMember',
        ]);
    }

    public static function accessRules() {
        return [
            'USER_EDIT' => [  // -- Access Name
                'editForm',   // -- Methods
                'edit'
            ],
            'USER_CREATE' => [
                ...
            ]
        ];
    }

    public function editForm() {
        .....
    }

    public function edit(Request $request) {
        .....
    }

替代方案

一种简单的保护方法,无需设置中间件和控制器访问规则。

在控制器方法中调用 auth()->guardAccess($accessName),如果抛出404则阻止访问。

    public function editForm() {
        auth()->guardAccess('USER_EDIT');

        ...
    }

您还可以添加错误回调,

    public function editForm() {
        auth()->guardAccess('USER_EDIT', function() {
            throw new Exception("Access Denied");
        });

        ... 
    }

或者使用助手

    public function editForm() {
        if (!auth()->hasAccess('USER_EDIT')) {
            return [
                "error" => "Access Denied."
            ];
        }

        ... 
    }

助手

Blade 指令

按访问名称组织blade布局

    @hasAccess('USER_EDIT') 
        .....
    @endhasAccess

Auth 助手

如果您需要检查当前用户是否具有访问特定访问名称的权限

    auth()->hasAccess('USER_EDIT');