Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Laravel Authentication Acl Laravel Package

jacopo/laravel-authentication-acl

Laravel Authentication ACL provides a complete authentication and access control system: users, roles, permissions, login, registration, password reset, social login, and an admin interface for managing users and permissions.

View on GitHub
Deep Wiki
Context7

Getting Started

This package is a Laravel 4/5-era drop-in auth + ACL + admin panel. It is archived (no maintenance), so treat it as legacy integration work: pin it to the Laravel version its composer.json supports (roughly Laravel 5.0–5.5 / PHP 7.0–7.1) and do not attempt to modernise it in place — the cost of porting usually exceeds rewriting with spatie/laravel-permission + Laravel Breeze/Jetstream.

Minimum steps:

  1. composer require jacopo/laravel-authentication-acl (check the latest tag compatible with your Laravel version first — release notes on the repo list supported Laravel versions).
  2. Register the service provider in config/app.php (Jacopo\Authentication\AuthenticationServiceProvider) and the facades/aliases it publishes.
  3. Publish config and assets: the package exposes laravel-acl config, migrations, views and public assets. Publish all of them so you can override views without touching vendor/.
  4. Drop Laravel's stock create_users_table migration — this package ships its own users, roles, permissions, role_user, permission_role, user_profiles, and social-login tables, and they collide.
  5. Run php artisan migrate, then seed the default roles/permissions (the package ships seeders and a config array of default roles/permissions — seed them before creating your first user).
  6. Set the auth model in config/auth.php to Jacopo\Authentication\Models\User (or the package model your version exposes). The admin panel and Auth::user() will not behave correctly otherwise.
  7. Hit /login, /signup and /admin — the url_prefix, login/signup toggles and admin path all live in the published laravel-acl config.

First use case: register a user via /signup, manually attach the admin role in the role_user table, then log into /admin to manage users, roles and permissions from the UI. That single loop validates the whole stack (routes, middleware, guard, ACL tables).

Where to look first: the published config file (it documents the package's extension points better than the README), the package's routes.php, and the Models/ directory — User, Role, Permission, UserProfile define the schema your app will actually query.

Implementation Patterns

Auth guard vs. Laravel auth. The package pre-dates Auth::guard() and Gate/Policy, so day-to-day you work through its own facade/interface rather than Laravel's native can(). In this codebase:

use Illuminate\Support\Facades\Auth;

$user = Auth::user();                         // Jacopo\Authentication\Models\User
$user->hasRole('admin');                     // role check
$user->hasPermission('users.list');          // permission check
$user->userProfile->first_name;              // profile is a relation, not columns on users

Keep these checks in filters/middleware and controllers, and avoid scattering string literals — define permission names in one constants class and reference them from Blade partials too.

Route protection. Apply the package's admin middleware/filter to a route group rather than checking roles inside every controller action:

Route::group(['middleware' => ['web', 'auth.admin']], function () {
    Route::get('/reports', 'ReportController@index');
});

For your own feature-level ACL (not admin), wrap a route group with a custom middleware that calls hasPermission() and aborts 403.

Extending the admin panel. The panel is a normal controller + Blade stack you can extend without forking:

  • Override views by publishing them and editing the copies; the config's view namespace controls which files are picked up.
  • Add admin menu entries by editing the published admin layout partial rather than the vendor layout.
  • Add your own admin controllers under the same route group so they inherit auth.admin and the panel's layout.
  • Use the package's base controller/helpers where available so flash messages, breadcrumbs and validation errors render consistently.

User lifecycle hooks. Registration, email confirmation and password reset are handled by the package's controllers. Rather than overriding controllers, add your own logic in model events or by extending the package's user model:

class User extends \Jacopo\Authentication\Models\User
{
    protected static function boot()
    {
        parent::boot();
        static::created(function ($user) {
            // provision tenant, send welcome mail, assign default role
        });
    }
}

Then point config/auth.php (and the package config, if it names a user class) at your subclass.

Authorization in Blade. Because there's no Gate, create a tiny helper/partial:

@if (Auth::user() && Auth::user()->hasPermission('invoices.manage'))
    <a href="{{ route('invoices.index') }}">Invoices</a>
@endif

Cache the permission list per request (a $permissions array set by a middleware) if you render menus with many checks — the package hits the DB per call.

Integration with an existing app. Use the package only for auth + ACL and let your app own the rest: keep your domain tables keyed on users.id, and treat user_profiles as the canonical place for names/avatars so the admin panel stays coherent. If you need social login, configure providers in the package config; it delegates to Socialite, so app credentials and callback URLs must match the package's routes.

Gotchas and Tips

  • It is archived. No Laravel 6+/PHP 8 support; expect failures on str_random, array_except semantics, middleware registration differences, and Symfony/Illuminate signature changes. Pin every dependency and commit the lock file. For new work, budget a rewrite instead.
  • users table collision is the #1 install failure. Remove Laravel's stock users migration before migrate, and check the published migrations for a user_profiles foreign key ordering issue (profiles must migrate after users).
  • Guard model mismatch. Forgetting to set the auth model causes "Call to undefined method hasPermission()" on Auth::user(), because you get the stock App\User instead. Also clear config:cache after changing it.
  • Roles vs. permissions are separate tables. Assigning a role doesn't auto-grant anything unless the role is linked in permission_role. Seed the default role→permission mappings, or the admin panel look right while every check returns false.
  • Admin middleware is registered differently across versions. In older releases it's a route filter in app/Http/filters.php (or routes.php for L4); in later ones a middleware in Kernel.php. Match the pattern used by your pinned version — mixing them silently disables protection. Verify by hitting /admin while logged out; it must redirect, not 500 or render.
  • Views and assets are published copies, not vendor reads. After upgrading the package, re-publish or diff the views; stale copies are a common source of "my change did nothing". Same for the config: vendor:publish --force will overwrite your customisations — back up first.
  • Profile fields live on user_profiles, not users. Queries like User::where('first_name', ...) fail; join user_profiles. Registration creates the profile row — if you create users programmatically, create the profile too.
  • Email confirmation / activation is configurable and easy to leave half-on: check whether new users are activated/confirmed by default in config, and whether your tests bypass it. This bites when seeding admin users by hand.
  • Password reset and mail use the package's own views and Laravel's mailer config of that era — verify MAIL_* and the reset route names before demoing; broken links usually come from APP_URL/route name drift, not the package.
  • Social login needs provider credentials plus exact callback URLs (/login/{provider}/callback by default). A mismatch produces a generic Socialite exception that surfaces as a 500 — check storage/logs/laravel.log, not the UI.
  • Debugging ACL denials: log hasRole/hasPermission inputs and the user id, and inspect role_user / permission_role directly. Most "it's broken" reports are stale seed data or a user with no roles after a manual insert.
  • Performance: permission checks are per-call DB queries in the default implementation. For large menus, memoise per request; don't rely on a cache layer the package doesn't provide.
  • Route cache: php artisan route:cache can break the package's closure-based routes on older Laravel versions. If /admin 404s in production but works locally, that's your culprit.
  • Migration to something maintained: if the app must live on, isolate the package behind your own Authenticator/Authorization interfaces early so replacing it with spatie/laravel-permission + a modern starter kit is a swap, not a rewrite.
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
socialdept/atp-orm
cboxdk/laravel-assistant-client
socialdept/atp-resolver
socialdept/tenant-domains
tautvydasr/blade-class-names
socialdept/color-scales
maherelgamil/controller
coleus/widgets
coleus/table
coleus/users
coleus/music
coleus/health
coleus/calendar
coleus/notes
coleus/support
coleus/settings
coleus/apps
seampact/laravel
emmyconceptng/laravel-ng-postcode
jjsquady/round-robin