manoyeche / imachable
Imachable - 使用提供给用户的访问列表来为控制器方法添加保护,而不是使用路由。
v0.0.12
2021-03-09 04:01 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');