VOOZH about

URL: https://deepwiki.com/hypervel/permission/4-database-schema-and-models

⇱ Database Schema and Models | hypervel/permission | DeepWiki


Loading...
Menu

Database Schema and Models

Purpose and Scope

This document provides comprehensive documentation of the database schema and Eloquent models that form the persistence layer of the Hypervel Permission package. It covers the five-table structure that implements role-based access control (RBAC) with support for direct permission assignments, role-based permission inheritance, and polymorphic owner relationships.

For detailed migration implementation, see Database Migrations. For specific model implementations, see Role Model and Permission Model. For how these models integrate with authorization logic, see HasPermission Trait and HasRole Trait.

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php1-89 src/Models/Role.php1-49 src/Models/Permission.php1-49

Schema Overview

The database schema consists of five interconnected tables that implement a flexible RBAC system with polymorphic relationships. The schema supports:

  • Named roles and permissions with guard contexts
  • Many-to-many relationships between roles and permissions
  • Polymorphic assignment of roles to any owner entity type
  • Polymorphic assignment of permissions to any owner entity type
  • Negative permissions (explicit denials) via is_forbidden flags

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php28-74

Table Structure

Core Entity Tables

The schema defines two core entity tables that store the fundamental authorization primitives:

TablePrimary KeyUnique ConstraintsIndexesPurpose
rolesidname (unique)(name, guard_name)Stores role definitions
permissionsidname (unique)(name, guard_name)Stores permission definitions

Both tables share identical structure:


The composite index on (name, guard_name) enables efficient lookups when resolving permissions and roles within specific guard contexts.

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php28-43

Pivot Tables

The schema includes three pivot tables that implement the many-to-many relationships:

TableComposite Primary KeyAdditional IndexesSpecial Columns
role_has_permissions(permission_id, role_id)role_id, permission_idis_forbidden
owner_has_permissions(permission_id, owner_id, owner_type)owner_id, permission_idis_forbidden
owner_has_roles(role_id, owner_id, owner_type)owner_id, role_idNone

role_has_permissions

This table links roles to their associated permissions and includes the is_forbidden flag to support negative permissions (explicit denials).


Sources: database/migrations/2025_07_02_000000_create_permission_tables.php44-53

owner_has_permissions

This polymorphic pivot table enables direct permission assignment to any entity type (User, Team, etc.). The polymorphic relationship uses owner_type (fully qualified class name) and owner_id columns.


The morphs('owner') macro creates both owner_type and owner_id columns, enabling any model class to own permissions.

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php55-64

owner_has_roles

This polymorphic pivot table assigns roles to owner entities. Unlike the permission pivots, it does not include an is_forbidden flag because role denial is handled at the permission level.

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php66-74

Model Architecture

The package provides two Eloquent models that map to the core entity tables. These models implement trait-based authorization logic and define relationships to pivot tables.


Sources: src/Models/Role.php22-24 src/Models/Permission.php22-24

Role Model

The Role model (src/Models/Role.php22) represents a role entity and includes the HasPermission trait, allowing roles themselves to have permissions. This creates the role-permission association.

Key characteristics:

  • Implements RoleContract interface
  • Uses HasPermission trait for permission management
  • Defines permissions() relationship to the pivot table
  • Mass assignable: name, guard_name

The model defines a BelongsToMany relationship to permissions:


Sources: src/Models/Role.php1-49

Permission Model

The Permission model (src/Models/Permission.php22) represents a permission entity and includes the HasRole trait, creating the inverse relationship where permissions can query which roles have them.

Key characteristics:

  • Implements PermissionContract interface
  • Uses HasRole trait for role management
  • Defines roles() relationship to the pivot table
  • Mass assignable: name, guard_name

Sources: src/Models/Permission.php1-49

Polymorphic Relationships

The schema's polymorphic design enables any model to become an authorization owner by using the HasPermission and HasRole traits. The polymorphic columns store the owner's class name and primary key.


When a model uses HasPermission or HasRole, it gains methods that interact with these polymorphic pivot tables. For example:

  • User::find(1)->permissions queries owner_has_permissions where owner_type='App\Models\User' and owner_id=1
  • Team::find(5)->roles queries owner_has_roles where owner_type='App\Models\Team' and owner_id=5

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php55-74 src/Models/Role.php24 src/Models/Permission.php24

Key Schema Features

Guard Name Context

Both roles and permissions tables include a guard_name column that provides multi-authentication context support. This allows the same permission or role name to exist in different guard contexts (e.g., 'web', 'api', 'admin').

The composite index (name, guard_name) on both tables ensures efficient lookups within guard contexts and enforces uniqueness per guard.

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php31-42

is_forbidden Flag

The is_forbidden boolean column in both role_has_permissions and owner_has_permissions pivot tables implements negative permissions (explicit denials). This flag enables:

  • Role-level permission denial: a role can explicitly forbid a permission
  • Owner-level permission denial: an owner can explicitly forbid a permission, overriding role grants

The authorization logic in HasPermission trait checks this flag during permission evaluation, with denials taking precedence over grants.

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php47-58 src/Models/Role.php46 src/Models/Permission.php46

Configurable Names

All table names, column names, and model class references are loaded from configuration, allowing customization without modifying migration files:

Configuration KeyDefault ValuePurpose
permission.models.roleRole::classRole model class
permission.models.permissionPermission::classPermission model class
permission.table_names.role_has_permissionsrole_has_permissionsPivot table name
permission.column_names.role_pivot_keyrole_idRole foreign key
permission.column_names.permission_pivot_keypermission_idPermission foreign key

This configurability appears in the model relationship definitions where config() calls retrieve these values.

Sources: src/Models/Role.php39-43 src/Models/Permission.php39-43

Database Connection Configuration

The migration supports a custom database connection via the permission.storage.database.connection configuration key, enabling the permission tables to reside in a separate database from the main application.

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php15-19

Relationship Summary

The complete relationship graph shows how all five tables interconnect:


This schema design achieves:

  1. Flexibility: Any entity can have roles and permissions via polymorphic relationships
  2. Inheritance: Owners gain permissions through roles via role_has_permissions
  3. Override capability: Direct permissions on owners can override role-based permissions
  4. Negative permissions: is_forbidden flags enable explicit denials
  5. Multi-tenancy: guard_name separates authorization contexts

Sources: database/migrations/2025_07_02_000000_create_permission_tables.php28-74 src/Models/Role.php37-47 src/Models/Permission.php37-47