Skip to content

ACL Matrix

The ACL (Access Control List) page provides a matrix view for managing role-based permissions.

ACL permission matrix

Overview

The ACL interface displays:

  • Left panel — controller tree grouped by plugin and prefix
  • Main panel — permission matrix for the selected controller

Permission matrix

The matrix shows:

  • Rows — actions for the selected controller
  • Columns — available roles (ordered by hierarchy)
  • Cells — permission state

Permission states

StateDisplayMeaning
NoneGray (empty)No explicit permission — access denied
AllowGreen checkmarkAccess granted for this role
DenyRed XAccess explicitly denied (overrides inherited allow)

Setting permissions

Click on any cell to cycle through permission states:

  1. None → Allow
  2. Allow → Deny
  3. Deny → None

Instant save

Changes are saved immediately via HTMX — there is no separate save button.

Permission logic

  1. If a role has an explicit deny for an action, access is denied.
  2. If a role has an explicit allow for an action, access is granted.
  3. If no explicit permission exists, access is denied by default.

Role hierarchy

Permissions can be inherited through role hierarchy:

text
admin (level 3)
  └── moderator (level 2)
        └── user (level 1)

When checking permissions:

  • Admin inherits all permissions from moderator and user.
  • Moderator inherits all permissions from user.
  • Higher roles automatically have lower-role permissions.

See Roles for the full hierarchy model.

Use the search box to quickly find:

  • controllers by name
  • actions by name
  • roles by name or alias

Database schema

sql
-- Controllers table
CREATE TABLE tinyauth_controllers (
    id INT AUTO_INCREMENT PRIMARY KEY,
    plugin VARCHAR(100) NULL,
    prefix VARCHAR(100) NULL,
    name VARCHAR(100) NOT NULL,
    created DATETIME,
    modified DATETIME,
    UNIQUE KEY (plugin, prefix, name)
);

-- Actions table
CREATE TABLE tinyauth_actions (
    id INT AUTO_INCREMENT PRIMARY KEY,
    controller_id INT NOT NULL,
    name VARCHAR(100) NOT NULL,
    is_public BOOLEAN DEFAULT FALSE,
    created DATETIME,
    modified DATETIME,
    UNIQUE KEY (controller_id, name),
    FOREIGN KEY (controller_id) REFERENCES tinyauth_controllers(id)
);

-- ACL permissions table
CREATE TABLE tinyauth_acl_permissions (
    id INT AUTO_INCREMENT PRIMARY KEY,
    action_id INT NOT NULL,
    role_id INT NOT NULL,
    type ENUM('allow', 'deny') NOT NULL,
    created DATETIME,
    modified DATETIME,
    UNIQUE KEY (action_id, role_id),
    FOREIGN KEY (action_id) REFERENCES tinyauth_actions(id),
    FOREIGN KEY (role_id) REFERENCES tinyauth_roles(id)
);

Programmatic access

php
use TinyAuthBackend\Service\TinyAuthService;

$service = new TinyAuthService();

// Check if a user has access to an action
$hasAccess = $service->hasAccess($user, 'Articles', 'edit');

// Check with plugin/prefix
$hasAccess = $service->hasAccess($user, 'Articles', 'edit', [
    'plugin' => 'Blog',
    'prefix' => 'Admin',
]);

Bulk operations

To set permissions for all actions in a controller:

php
$actionsTable = $this->fetchTable('TinyAuthBackend.Actions');
$permissionsTable = $this->fetchTable('TinyAuthBackend.AclPermissions');

$actions = $actionsTable->find()
    ->where(['controller_id' => $controllerId])
    ->all();

foreach ($actions as $action) {
    $permission = $permissionsTable->newEntity([
        'action_id' => $action->id,
        'role_id' => $roleId,
        'type' => 'allow',
    ]);
    $permissionsTable->save($permission);
}

// Clear cache
Cache::delete('TinyAuth.acl');

See also

Released under the MIT License.