我正在做一个大型的Laravel项目,它有5种用户类型,大约50种型号和相同数量的控制器。
每个用户类型都有自己的权限,根据不同的因素从单独的表中计算,因此一个简单的模型策略无法工作。
到目前为止,我所做的是为每个模型创建一个策略,并在那里进行计算:
class MyModelPolicy {
function someActionName(){
// Check whether user have the permission or not.
// I only return a simple true/false here, as I might need to
// reuse this somewhere else.
return $resultAsBoolean;
}
}现在,在控制器中,我使用了一个使用Gate外观并抛出自定义异常的助手函数:
function checkUserAccess( $someActionName, $args = [ 'some arguments' ] ){
$gate = Gate::inspect( $someActionName, $args );
if( $gate->denied() ) {
// Throw exception here
throw new PermissionDeniedException( 'message here' );
}
}而控制器本身:
public function store(){
// Check permissions
checkUserAccess('permissions to check');
// All good, continue
}在最后一部分中,我定义了一个自定义异常,它扩展了基本的Laravel,并且有一个render()方法来决定要做什么:
class PermissionDeniedException extends Exception {
public function render(){
/**
* Our custom permissionDeniedException has been
* triggered. Do the right action based on the
* current situation. This will always terminate the app.
*/
}
}现在我知道将异常用于流控制不是一个好主意,但是由于这个异常将完全终止应用程序,我并不觉得使用它很糟糕。但是,这里唯一的问题是,我的控制器的每个方法(大约350次)现在都可以抛出一个异常。我想通过将所有方法设置为私有来解决这个问题,然后使用__call()魔术方法,然后只从那里抛出异常。
有什么更好的解决办法吗?或者,当项目变得过于复杂时,这是不可避免的吗?
发布于 2021-11-07 22:12:47
抛出异常是处理流的一种正常方法,它必须终止并具有特定的响应。这与例外的Handler.php很好地结合在一起。
你的解决方案是好的,但一般来说,你想要做的事情有语法糖。如下图所示,如果权限不存在,则将引发Illuminate\Auth\Access\AuthorizationException。
Gate::authorize('permissions to check', $yourModel);然而,这里唯一的问题是,我的控制器的每个方法(大约350个总数)现在都可以抛出一个异常。
这是一个没有问题,想象一下,如果您使用模型绑定,例如。用URl参数进行模型注入。从所有使用的地方,它可以抛出一个ModelNotFoundException。这些问题将由异常Handler.php处理,我认为没有什么可担心的。
https://stackoverflow.com/questions/69876206
复制相似问题