当用户请求在 Laravel 中删除多条记录时,如何检查每个结果的策略?

问题描述 投票:0回答:1

我在控制器中有一个方法

bulk_destroy
,它接受用户想要删除的 id 数组。我必须检查每条记录,用户是否是该记录的所有者,或者他是否具有删除该记录的特定角色。

最后我必须返回所有被删除的记录 ID 以及用户没有特定角色的剩余记录 ID。有没有什么有效的方法可以根据角色删除记录。


我可以考虑的一种方法是,我将获取记录,然后迭代每条记录,对于每条记录,我将检查登录用户是否是该记录的所有者或者他具有特定角色或不是。如果他有那么我会删除该记录。如下所示:

$posts = Post::withTrashed()->whereIn('_id', $request->ids);
$deleted_post_ids = [];
$not_deleted_post_ids = [];
foreach($posts as $post) {
    if ($post->owner_id == auth()->id() || auth()->user()->hasAnyRole(['super-admin', 'admin', 'moderator']) {
      array_push($deleted_post_ids, $post->forceDelete());
    }
    else {
      array_push($not_deleted_post_ids, $post->id);
    }
}

return response()->json([
    'success' => [
        'message' => 'posts deleted successfully',
        'ids' => $deleted_post_ids,
    ],
    'error' => [
        'message' => 'not authorized',
        'ids' => $not_deleted_post_ids,
    ],
], 200);

但在这种情况下,对于每条记录,它都会进行数据库查询来删除该记录,我认为这不是正确的方法。


我能想到的其他解决方案是:

$posts = Post::withTrashed()->whereIn('_id', $request->ids);
$deleted_post_ids = [];
$not_deleted_post_ids = [];

if (!auth()->user()->hasAnyRole(['super-admin', 'admin', 'moderator'])
{
  $posts = $post->where('owner_id', auth()->id());
}

$deleted_post_ids = $posts->forceDelete();
$not_deleted_post_ids = array_diff($request->ids, $deleted_post_ids);

实际上我正在考虑以下解决方案:

$posts = Post::withTrashed()->whereIn('_id', $request->ids);
$deleted_post_ids = $posts->forceDelete(); // it should take care of authorization

但是如何约束

forceDelete()
仅删除特定记录。有什么方法可以覆盖
forceDelete()
方法吗?

或者一些优雅的解决方案非常感谢。


更新

我不能使用策略,因为如果我使用,

$user->can('deleteBulk', [Post::class, $ids]);

它返回true/false,那么我如何只删除用户有权访问的资源呢?因为在某些情况下

$ids
可能包含授权和未经授权的 ID 的混合。

php laravel laravel-5 laravel-permission jenssegers-mongodb
1个回答
1
投票

如果您使用启用策略的包,您是否不应该检查策略是否允许身份验证用户删除资源?

您“可以”构建一个接受多个 ID 的策略方法,没有什么可以阻止您这样做,但大多数策略可能最适合资源实例。

示例:

$user->can('deleteBulk', [Post::class, $ids]);

由于删除通常不会在应用程序中经常执行,因此在删除之前选择所有资源并单独传递每个实例以检查授权可能听起来效率低下,但实际上不会那么明显。

阅读 laravel 授权策略方法,了解有关编写策略的更多信息。唯一需要存在的参数是 $user,除此之外,您可以定义在方法中传递和使用的内容。

© www.soinside.com 2019 - 2024. All rights reserved.