- Creating Permissions
- Checking Permissions
- Working with Groups
- Working with Teams
- Understanding Effects
- Common Patterns
use Pbac\Models\PBACAccessControl;
use App\Models\Post;
// Allow a user to view a specific post
PBACAccessControl::factory()
->allow()
->forUser($user)
->forResource(Post::class, $post->id)
->withAction('view')
->create();// Allow multiple actions on the same resource
PBACAccessControl::factory()
->allow()
->forUser($user)
->forResource(Post::class, $post->id)
->withAction(['view', 'edit', 'delete'])
->create();// Allow user to view ALL posts (resource_id = null)
PBACAccessControl::factory()
->allow()
->forUser($user)
->forResource(Post::class, null) // null = any post
->withAction('view')
->create();// For "create" actions, use class name since resource doesn't exist yet
PBACAccessControl::factory()
->allow()
->forUser($user)
->forResource(Post::class, null)
->withAction('create')
->create();
// Check permission
if ($user->can('create', Post::class)) {
// User can create posts
}if ($user->can('view', $post)) {
// User can view this post
}
if ($user->cannot('edit', $post)) {
// User cannot edit this post
}use Illuminate\Support\Facades\Gate;
// Using Gate facade
if (Gate::allows('edit', $post)) {
// Allowed
}
if (Gate::denies('delete', $post)) {
// Denied
}
// Throw exception if denied
Gate::authorize('publish', $post);@can('edit', $post)
<button>Edit Post</button>
@endcan
@cannot('delete', $post)
<p>You cannot delete this post</p>
@endcannot
{{-- Using PBAC directive --}}
@pbacCan('publish', $post)
<button>Publish</button>
@endpbacCan// Check if user has ANY of the permissions
if (Gate::any(['edit', 'delete'], $post)) {
// User has either edit OR delete permission
}
// Check if user has NONE of the permissions
if (Gate::none(['edit', 'delete'], $post)) {
// User has neither edit NOR delete permission
}use Pbac\Models\PBACAccessGroup;
$editors = PBACAccessGroup::create([
'name' => 'Editors',
'description' => 'Users who can edit content'
]);// Add single user
$user->groups()->attach($editors->id);
// Add multiple users
$editors->users()->attach([$user1->id, $user2->id, $user3->id]);// All group members will have this permission
PBACAccessControl::factory()
->allow()
->forGroup($editors)
->forResource(Post::class, null)
->withAction(['view', 'edit'])
->create();// Get all groups for a user
$groups = $user->groups;
// Check if user belongs to a group
if ($user->groups->contains($editors)) {
// User is an editor
}
// Count groups
$groupCount = $user->groups()->count();// Remove single user
$user->groups()->detach($editors->id);
// Remove from all groups
$user->groups()->detach();use Pbac\Models\PBACAccessTeam;
$devTeam = PBACAccessTeam::create([
'name' => 'Development Team',
'description' => 'Software developers',
'owner_id' => $user->id // Optional
]);// Add users to team
$user->teams()->attach($devTeam->id);
// Or from team side
$devTeam->users()->attach([$user1->id, $user2->id]);// All team members will have this permission
PBACAccessControl::factory()
->allow()
->forTeam($devTeam)
->forResource(Project::class, null)
->withAction('*') // All actions
->create();Teams are perfect for multi-tenant applications:
// Team A can only see Team A's data
PBACAccessControl::factory()
->allow()
->forTeam($teamA)
->forResource(Document::class, null)
->withAction('view')
->create([
'extras' => [
'requires_attribute_value' => [
'team_id' => $teamA->id
]
]
]);// Allow effect - grants permission
PBACAccessControl::factory()
->allow() // effect = 'allow'
->forUser($user)
->forResource(Post::class, $post->id)
->withAction('view')
->create();
// Deny effect - blocks permission
PBACAccessControl::factory()
->deny() // effect = 'deny'
->forUser($user)
->forResource(Post::class, $secretPost->id)
->withAction('view')
->create();IMPORTANT: Deny rules ALWAYS override allow rules, regardless of priority!
// Even with very high priority...
PBACAccessControl::factory()
->allow()
->forUser($user)
->forResource(Post::class, $post->id)
->withAction('view')
->withPriority(1000) // Very high priority
->create();
// ...a deny with low priority still wins
PBACAccessControl::factory()
->deny()
->forUser($user)
->forResource(Post::class, $post->id)
->withAction('view')
->withPriority(1) // Low priority
->create();
// Result: Access DENIED (secure by default)
$user->can('view', $post); // false// Create a "Users" group
$users = PBACAccessGroup::create(['name' => 'All Users']);
// Add all new users to this group automatically
// In your User model or registration logic:
public static function boot()
{
parent::boot();
static::created(function ($user) {
$usersGroup = PBACAccessGroup::where('name', 'All Users')->first();
$user->groups()->attach($usersGroup->id);
});
}
// Grant default permissions to the group
PBACAccessControl::factory()
->allow()
->forGroup($users)
->forResource(Post::class, null)
->withAction('view')
->create();// Allow users to edit their own posts
PBACAccessControl::factory()
->allow()
->forUser($user)
->forResource(Post::class, null)
->withAction(['edit', 'delete'])
->create([
'extras' => [
'requires_attribute_value' => [
'user_id' => $user->id // Only if post.user_id matches
]
]
]);// Admins get all permissions
PBACAccessControl::factory()
->allow()
->forGroup($admins)
->forResource(null, null) // Any resource
->withAction('*') // Any action
->create();
// Moderators get limited permissions
PBACAccessControl::factory()
->allow()
->forGroup($moderators)
->forResource(Post::class, null)
->withAction(['view', 'edit'])
->create();
// Users get basic permissions
PBACAccessControl::factory()
->allow()
->forGroup($users)
->forResource(Post::class, null)
->withAction('view')
->create();// Grant access that expires
$expiresAt = now()->addDays(7);
PBACAccessControl::factory()
->allow()
->forUser($user)
->forResource(Document::class, $doc->id)
->withAction('view')
->create([
'extras' => [
'expires_at' => $expiresAt->toDateTimeString()
]
]);
// You would need to implement expiration check in PolicyEvaluator
// or clean up expired rules with a scheduled job// Readers can view
PBACAccessControl::factory()
->allow()
->forGroup($readers)
->forResource(Post::class, null)
->withAction(['view', 'list'])
->create();
// Writers can view and modify
PBACAccessControl::factory()
->allow()
->forGroup($writers)
->forResource(Post::class, null)
->withAction(['view', 'list', 'create', 'edit', 'delete'])
->create();| Method | Purpose |
|---|---|
allow() |
Set effect to 'allow' |
deny() |
Set effect to 'deny' |
forUser($user) |
Set target to specific user |
forGroup($group) |
Set target to group |
forTeam($team) |
Set target to team |
forResource($class, $id) |
Set resource type and ID |
withAction($action) |
Set action(s) - string or array |
withPriority($int) |
Set priority (higher = evaluated first) |
create($attributes) |
Create the rule |
view- Read a resourcecreate- Create new resourceedit/update- Modify existing resourcedelete- Remove a resourcepublish- Publish/activate a resource*- Wildcard for all actions
- Advanced Usage - Conditions, priorities, and complex scenarios
- Use Cases - Common application patterns