Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/231.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php Laravel:如果用户在路由中手动输入ID,如何抛出403?_Php_Laravel_Laravel 5 - Fatal编程技术网

Php Laravel:如果用户在路由中手动输入ID,如何抛出403?

Php Laravel:如果用户在路由中手动输入ID,如何抛出403?,php,laravel,laravel-5,Php,Laravel,Laravel 5,构建应用程序(博客/帖子)。 其中只有授权用户可以编辑他们的帖子(当然这只属于他们)。 例如,id为15的帖子属于特定的用户,因此如果他编辑它,那么路由将如下所示 http://localhost:8000/post/15/edit 这是正确的 但当用户在路由中输入任何其他帖子ID(不属于他)时,它会显示 http://localhost:8000/post/16/edit ErrorException (E_NOTICE) Trying to get property 'user_id'

构建应用程序(博客/帖子)。 其中只有授权用户可以编辑他们的帖子(当然这只属于他们)。 例如,id为15的帖子属于特定的用户,因此如果他编辑它,那么路由将如下所示

http://localhost:8000/post/15/edit
这是正确的

但当用户在路由中输入任何其他帖子ID(不属于他)时,它会显示

http://localhost:8000/post/16/edit

ErrorException (E_NOTICE)
Trying to get property 'user_id' of non-object
在这种情况下如何显示未经授权的页面

这是后置控制器

public function edit($id)

{

$post = Post::find($id);

        if(Auth::user()->id == $post->user_id){

        return view('post-edit',compact('post'));
    }else {
        return redirect()->route('home');      

}
}

下面的代码检查post是否存在(这就是为什么您在尝试获取非对象的属性“user\u id”(因为它不存在)时出现错误的原因),然后检查它是否属于处于相同条件下的用户。如果无效,它将以403未经授权的错误代码中止

public function edit($id)
{
    $post = Post::find($id);
    if (empty($post) || Auth::id() != $post->user_id) {
        abort(403);
    }
    else {
        return view('post-edit',compact('post'));      
    }
}
下面是一个更好的版本,它可以使用指定的ID检查post是否存在,也可以使用正确的用户检查post,否则会引发异常:

public function edit($id)
{
    $post = Post::whereHas('user', function ($q) {
        $q->where('users.id', Auth::id());
    })->findOrFail($id);

    return view('post-edit',compact('post'));      
}
第三个版本,与第二个版本的想法相同,但更简单:

public function edit($id)
{
    $post = Post::where('user_id', Auth::id())->findOrFail($id);

    return view('post-edit',compact('post'));      
}

使用laravel授权策略对用户进行授权

php artisan make:policy PostPolicy --model=Post
此命令将在app\policiesdir中创建PostPolicy.php。 现在,您必须在AuthServiceProvider中注册策略。例如,首先添加策略和模型的use语句

use App\Post;
use App\Policies\PostPolicy;
然后找到受保护的$policies,并在该数组中注册策略。政策遵循的模式

protected $policies = [
    Post::class => PostPolicy::class,
];
现在,在我们使用artisan命令生成的策略中。将保存所有与积垢相关的方法。它们中的每一个都接受两个参数,一个是用户,另一个是除create方法外您要授权的模型。请注意,您可以修改create或其他方法以接受更多参数。由你决定

现在,例如在您的策略中,让我们为更新方法构建逻辑

/**
 * Determine if the given post can be updated by the user.
 *
 * @param  \App\User  $user
 * @param  \App\Post  $post
 * @return bool
 */
public function update(User $user, Post $post)
{
    return $user->id === $post->user_id;
}
正如您在这里看到的,返回布尔值。您可以根据需要自定义方法。接下来是控制器方法。在您想要授权用户的地方,只需添加

public function update(Post $post)
{
    $this->authorize('update', $post);
    // then your logic here.
}
对于创建授权,只需传递空类

$this->authorize('create', Post::class);
它接受两个参数,一个是授权方法名称,另一个是模型。它自动获取用户的身份验证用户和授权用户。如果未授权,则抛出403的
illumb\Auth\Access\AuthorizationException

此外,如果需要修改403错误视图,则需要在中创建403刀片

resources/views/errors/403.blade.php
每件事都有很好的文档记录

额外提示如果要对从数据库返回的tinyint值使用布尔数据类型值,则为1或0。比如说

public function view(User $user, Post $post)
{
    if(! $post->isPrivate) {
       return true;
    }
    return $user->id === $post->user_id;
}

然后确保将该值转换为模型中的布尔值,以返回true或false。因为当我在共享主机上部署我的应用程序时,它不工作。后来我发现它以字符串的形式返回。数据库的版本也是旧的

404页未找到-您正在查找403页。为此,类似于<代码>如果($post_author!=$current_user){exit(“Error msg”);}-我不知道你的变量,所以这是一个猜测。谢谢但是在这种情况下如何抛出403呢?在本例中出现的错误是,您在代码中访问的变量(
$user\u id
)在您访问它的类中不存在-确保它已声明并设置我已编辑我的问题并添加了PostController