Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

Adam_Commit's avatar

Laravel Policies - 2 possible conditions

Hi community,

I have been racking me brain over this one, that seems like it should be terrribly easy.

I am building a system that allows commenting, I have built this out in laravel and vue js.

So far the CRUD actions are all working etc. My issue is with regards policies for authorized actions.

What I am trying to achieve is simply - both the commeter (the user who comments on a specific post) and author (of that specific post) both have permission/authorization to delete the comment.

I have a CommentPolicy (and had it working for just the owner of the comment to delete, this currently returned 403 if not the owner) but I can't seem to add-in permission for the project owner to also delete - which is an important attribute, the type of policy will be well used within the site so want to get it right.

CommentPolicy.php

<?php

namespace App\Policies;

use App\Comment;
use App\Project;
use App\User;
use Illuminate\Auth\Access\HandlesAuthorization;

class CommentPolicy
{
    use HandlesAuthorization;

    //Does the authenticated user own the comment (only commenter can udpate)
    public function update(User $user, Comment $comment){
        return $comment->user_id === $user->id;
    }
    //Commenter (user who made comment) or Author of project can delete
    public function delete(User $user, Project $project, Comment $comment){
        return $user->is($comment->project->owner) || $comment->user_id === $user->id;
    }
}

CommentController.php (very simple - specifically looking here at the destroy method at the bottom)

<?php

namespace App\Http\Controllers;

use App\Comment;
use App\Project;
use Illuminate\Http\Request;

class CommentController extends Controller
{
    public function index()
    {
        $comments = Comment::with('user')
            ->orderByDesc('id')
            ->get();
        return response($comments, 200);
    }

    public function show(Project $project)
    {
        $comments = $project->comments;

        return response($comments, 200);
    }

    public function store(Request $request)
    {

        //dd($request->all());

        $data = $request->validate([
            'body' => 'required|string',
            'projectID' => 'required'
        ]);

        $comment = auth()->user()
            ->comments()
            ->create([
                'body' => $data['body'],
                'project_id' => $data['projectID']
            ]);


        $comment->load('user');

        return response($comment, 200);
    }

    public function update(Request $request, Comment $comment)
    {
        //Authorise use can update
        $this->authorize('update', $comment);


        $data = $request->validate([
            'body' => 'required|string'
        ]);
        $comment->body = $data['body'];
        $comment->save();
        $comment->load('user');
        return response($comment, 200);
    }

    public function destroy(Comment $comment, Project $project)
    {
        //Authorise use can delete
        $this->authorize('delete', $comment);


        $comment->delete();
        return response( null,204);
    }
}

When I try to add this policy - it returns only 403 even for the comment creator, so I am struggling how to work out, how to query these two specific conditions.

I do also have a ProjectsPolicy.php but I am not sure calling the authorize method twice seems correct.

For reference, the ProjectPolicy.php (used for editing projects by author)

<?php

namespace App\Policies;

use App\Project;
use App\User;
use Illuminate\Auth\Access\HandlesAuthorization;

class ProjectPolicy
{
    use HandlesAuthorization;

    //Does the authenticated user own the project
    public function update(User $user, Project $project){

        return $project->user_id === $user->id;

    }
}

Any pointers in the right directions would be amazing, policies seem the right way to go and super powerful :)

Cheers

0 likes
1 reply
Adam_Commit's avatar
Adam_Commit
OP
Best Answer
Level 6

UPDATE: Working solution

Basically, I was querying two models separately and trying to pass them both as parameters.

As there was already a relationship set up between Projects and Comments, and subsequently already a relationship set up between Projects and Users, I could grab these value IDs and query them against the current User ID. So (and as intended by laravel, hence my original problem) I don't need to try to access project model.

Update to comment policy:

    //Commenter (user who made comment) or Author of project can delete
    public function delete(User $user, Comment $comment){

        // User is commenter OR User is the original author of the post.
        return $comment->user_id === $user->id || $comment->project->user_id === $user->id;

    }

Hopefully may be of use to others if they stumble upon trying to authorize to different user types.

Cheers

Please or to participate in this conversation.