Why Gemfury? Push, build, and install  RubyGems npm packages Python packages Maven artifacts PHP packages Go Modules Debian packages RPM packages NuGet packages

Repository URL to install this package:

Details    
Size: Mime:

Webbing CMS - Users Module

Este módulo possui um sistema de autenticação de usuários, com funções para recuperação de senha e permissões de acesso (ACL)

Instalação

Inclua as seguintes linhas no composer.json para instalar o módulo

"repositories": [{
  "type": "composer",
  "url":  "https://php.fury.io/xka1LLxBsys-bkR4n8D2/webbingbrasil/"
}],

"require": {
    "webbingbrasil/users-module": "0.1.*",
}

Agora execute o seguinte comando para instalar as dependencias

composer update

Você vai encontrar o módulo no diretorio Modules/Users.

Auth Driver

Este módulo possui um Driver (cmsauth) de autenticação customizado, que permite a autenticação usando login ou email. Para usar este componento, altere o arquivo de configuração auth.php para:

'providers' => [
  'users' => [
      'driver' => 'cmsauth'
  ]
]

Reset Passwords

Por padrão, a recuperação de senha para o painel backend vai usar a configuração definida em auth.passwords.users.email Caso seja necessario uma configuração diferente para front/back, inclua mais um nivel usando a chave 'cmsauth', ficando:

'passwords' => [
    'users' => [
        'provider' => 'users',
        'email' => 'auth.emails.password',
        'table' => 'password_resets',
        'expire' => 60,
    ],
    'cmsauth' => [
        'provider' => 'users',
        'email' => 'users::emails.reminder',
        'table' => 'password_resets',
        'expire' => 60,
    ],
],

ACL

Create Roles

Assign Role(s) To User

Lets assign created roles to a User.

Note: You can pass an object, an array, role->id or just a slug.

$user = User::find(1);
// by object
$user->assignRole($roleAdmin);
// or by id
$user->assignRole($roleAdmin->id);
// or by just a slug
$user->assignRole('administrator');

Or multiple roles at once:

// multiple roles in an array
$user->assignRole(array($roleAdmin, $roleModerator));
// or mutiple role slugs separated by comma or pipe.
$user->assignRole('administrator, moderator');

Note: The system will throw an exception if role does not exists.

Revoke Role(s) From User

Similarly, you may revoke roles from user

Note: You can pass an object, an array, role->id or just a slug.

$user = User::find(1);
// by object
$user->revokeRole($roleAdmin);
// or by id
$user->revokeRole($roleAdmin->id);
// or by just a slug
$user->revokeRole('administrator');

Or multiple roles at once:

// multiple roles in an array
$user->revokeRole(array($roleAdmin, $roleModerator));
// or mutiple role slugs separated by comma or pipe.
$user->revokeRole('administrator, moderator');

Note: The system will throw an exception if role does not exists.

Sync Role(s) To User

You can pass an array of role objects,ids or slugs to sync them to a user.

$user->syncRoles([1,2,3]);
$user->syncRoles('administrator, moderator');
$user->syncRoles((array($roleAdmin, $roleModerator));

Note: The system will throw an exception if role does not exists.

Revoke All User Roles

You can revoke all roles assigned to a user.

$user->revokeAllRoles();

Create Permissions

Assign Permission(s) to Role

Lets assign created permissions to a Role.

Note: You can pass an object, an array, role->id or just name.

$roleAdmin = Role::first(); // administrator
// permission as an object
$roleAdmin->assignPermission($permUser);
// as an id
$roleAdmin->assignPermission($permUser->id);
// or by name
$roleAdmin->assignPermission('user');

Or multiple permissions at once:

// multiple permissions in an array
$roleAdmin->assignPermission(array($permUser, $permPost->id));
// or mutiple role slugs separated by comma or pipe.
$roleAdmin->assignPermission('user, 'post');

Note: The system will throw an exception if permission does not exists.

Revoke Permission(s) from Role

Similarly, you may revoke permissions from a role

Note: You can pass an object, an array, permission->id or just a name.

$roleAdmin = Role::first(); // administrator
// permission as an object
$roleAdmin->revokePermission($permUser);
// as an id
$roleAdmin->revokePermission($permUser->id);
// or by name
$roleAdmin->revokePermission('user');

Or multiple permissions at once:

// multiple permissions in an array
$roleAdmin->assignPermission(array($permUser, $permPost->id));
// or mutiple role slugs separated by comma or pipe.
$roleAdmin->assignPermission('user, 'post');

Note: The system will throw an exception if role does not exists.

Sync Role Permissions

You can pass an array of role objects,ids or slugs to sync them to a user.

$roleAdmin->syncPermissions([1,2,3]);
$roleAdmin->syncPermissions('user, post');
$roleAdmin->syncPermissions((array($permUser, $permPost));

Note: The system will throw an exception if role does not exists.

Revoke All Permissions From A Role

You can revoke all roles assigned to a user.

$roleAdmin->revokeAllPermissions();

Working With User Permissions

User permissions work same way as role permissions except the fact user permissions override the default role permissions.

An alias has set of permissions stored as json in database.

Adding User Permissions

$user = User::first();

// create crud permissions
// create.user, view.user, update.user, delete.user
// returns false if alias exists.
$user->addPermission('user');

// update permission on user alias
// set its permission to false
$user->addPermission('update.user', false);
$user->addPermission('view.phone.user', true);

// pass permissions array to user alias
$user->addPermission('user', [
     'view.phone' => true,
     'view.blog' => false
]);

Note: If alias or permission already exists, it will update the existing permission's value.

Removing User Permissions

// remove an alias
$user->removePermission('user');

// remove update permission from user
$user->removePermission('update.user');

$user->removePermission('user', [
     'view.phone'
     'view.blog'
]);

Get User Permissions

Get permissions assigned to a user. An array of key value pairs are returned having user permissions along with its role permissions. Of course user permissions override role ones.

$user = User::first();
$user->getPermissions();

Working With Permissions Inheritance

You can bind multiple permissions together so they inherit ones permission.

Why inheritance is needed?

In some cases, you have same permission but different approach to it on different roles. For example a client will have different permissions on an admin role and different on manager role. If we don't use inheritance we are bundled with a lot of validations like Auth::user()->can('view.client.as.manager|view.client.as.admin|view.client.as.webdev|...') and the list can go on with each type of role. To make it simpler, we use permission inheritance. We can just validate permission using Auth::user()->can('view.client') and that makes life a lot easier. Therefore, a single permission named client will work different for admin or other roles.

Let the example code speak.

NOTE: The example below will only work as expected with 'ntfs' => false set in the config/acl.php file. By default, this value is set to true, so update accordingly if this is how you want the permission inheritance to work.

I have changed the example below with a Teacher and Student roles.

First we create Roles.

        $roleTeacher = Role::create([
            'name'        => 'Teacher',
            'slug'        => 'teacher',
            'description' => 'Teacher [...]'
        ]);

        $roleStudent = Role::create([
            'name'        => 'Student',
            'slug'        => 'student',
            'description' => 'Student [...]'
        ]);

Now lets create Permissions for Teacher and Student.

        $permissionInternship = Permission::create([
            'name'        => 'internships',
            'slug'        => [ // an array of permissions.
                'create' => true,
                'view'   => true,
                'update' => true,
                'delete' => true,
            ],
            'description' => 'manage internships'
        ]);

        $permissionStudent = Permission::create([
            'name'        => 'internships.student',
            'slug'        => [ // an array of permissions only for student
                'create' => false,
            ],
            // we use permission inheriting.
            'inherit_id' => $permissionInternship->getKey(),
            'description' => 'student internship permissions'
        ]);

Note: inherit_id in internships.student. since internships.student inherit permissions from internships we can can forget about internships.student because now we recognize it as internships. so getPermissions will return array('internships' => [...permissions merged with internships.student...])

Lets assign those permissions to newly created roles.

$roleTeacher->assignPermission('internships');  // or assignPermission($permissionInternship->id)
$roleStudent->assignPermission('internships.student');

And then we can assign those roles to our user.

$user->assignRole($roleTeacher);
$user->assignRole($roleStudent);
//$user->revokeRole('teacher');

Finally, lets do our tests.

// user has teacher and student role
dump($user->can('create.internships')); // results true

// user has teacher role
dump($user->can('create.internships')); // results true

// user has student role
dump($user->can('create.internships')); // results false

dump($user->getPermissions());

Get Role Permissions

Get permissions assigned to a role.

$roleAdmin = Role::first();
$roleAdmin->getPermissions();

Get User Permissions

Get permissions assigned to a user. An array of key value pairs are returned having user permissions along with its role permissions. Of course user permissions override role ones.

$user = User::first();
$user->getPermissions();

Validate Permissions and Roles.

Validate Roles

Roles can be validated by calling is method.

Validate based on User.

Method is() supports comma for AND and pipe as OR operator. Or you can pass operator as a second param.

$user = User::first();
$user->is('administrator');
$user->isAdministrator();	// using method

// using pipe as OR operator
// any one role allowed will result to true.
$user->is('administrator|moderator');

// using comma as AND operator
// all roles defined must be allowed to result true.
$user->is('administrator,moderator');

// or pass second param as operator
$user->is(array('administrator', 'moderator'), 'or');

Validate Permissions

Permissions can be validated by calling can method.

Validate based on Role.

Method can() supports comma for AND and pipe as OR operator. Or you can pass operator as a second param.

$admin = Role::first();	// administrator
$admin->can('view.user');
$admin->canViewUser();	// using method.

// by an array
$admin->can(array('view.user', 'edit.user'));

// by an array with or operator
$admin->can(array('view.user', 'edit.user'), 'or');

// using pipe as OR operator
// any allowed permission will result to true.
$admin->can('view.user|edit.user|view.admin|delete.admin');

// using comma as AND operator
// all permissions defined must be allowed to result true.
$admin->can('view.user,edit.user,view.admin,delete.admin');

Validate based on User

$user = User::first();
$user->can('delete.user');
$user->canDeleteUser();	// using method

Blade Template Extensions

Blade helper extension lets you write a little less code and is more elegant.

// @if(Auth::check() && Auth::user()->is('admin|moderator'))
// would be
@role('admin|moderator')
    // content allowed for admin's only
@endrole

// @if(Auth::check() && Auth::user()->can('create.user|edit.user''))
// would be
@permission('create.user|edit.user')
    // content if user can edit or create users.
@endpermission

Protecting Routes using middleware

ACL determines if controller have resource methods (index, create, store, etc) or are RESTful. If method names are not resource (different than index, create, store), it goes with RESTful check (HTTP method GET, POST, PUT, DELETE).

In your project if neither of those are viable, protect_methods param must be defined to pass an array of methods which needs to be protected on crud.

For example, when a user views content it will be a GET request, so ACL will check if its a resource method, if not it goes restful and will know its GET method so view has to be protected, hence user must have view.user permission.

If you pass protect_methods, you define your own method names to protect resource.

 [
   'create' => ['store'],    // protects store() method on create.user (create.alias)
   'view'   => ['index', 'create', 'show', 'edit'],     // protects index(), create(), show(), edit() methods on view.user permission.
   'update' => ['update'],
   'delete' => ['destroy']
]

Params definitions.

  • validate if user has a role, ['is' => 'administrator']

  • validate if user has permissions, ['can' => 'view.admin, update.user']

  • protect controller methods, ['protect_alias' => 'user'], will use permission alias of user and will protect crud methods depending on the permissions of that alias.

    For example, if user has permission to view but not update. It will allow HTTP GET method but not PUT. if you need to provide your own controller methods to protect you have to define them as an array.

['protect_alias'  => 'user',
 'protect_methods' => [
          'create' => ['someMethod', 'anotherMethod'],
          'read'   => ['readMethod', 'showMethod'],
          'view'   => ['readMethod', 'showMethod'], // its same as read.
          'update' => ['editMethod'],
          'delete' => ['destroyMethod']
]];

Protect route group/resource

Protecting routes are easy. Following checks if user has an administrator role.

Route::group(['prefix' => 'user',
              'middleware' => ['auth', 'acl'],
              'is' => 'administrator'],
function () {
    Route::resource('user', 'UsersController');
});

Or check if user has an administrator role and has permissions create.user, delete.user

Route::group(['prefix' => 'user',
              'middleware' => ['auth', 'acl'],
              'is' => 'administrator',
              'can' => 'create.user, delete.user'],
function () {
    Route::resource('user', 'UsersController');
});

Or protect crud methods by user permission alias.

Route::group(['prefix' => 'user',
              'middleware' => ['auth', 'acl'],
              'is' => 'administrator',
              'can' => 'do.something',
              'protect_alias' => 'user'],
function () {
    Route::resource('user', 'UsersController');
});

Protect route

Protecting a single route is as easy as setting a group route. Simply use the same permission params.

Route::get('/dashboard', [
    'uses'        => 'DashboardController@index',
    'middleware'   => ['auth', 'acl'],
    'is'           => 'administrator',
    'can'          => 'view.dashboard']);

Or protect crud methods by dashboard alias.

Route::get('/dashboard', [
    'uses'          => 'DashboardController@index',
    'middleware'    => ['auth', 'acl'],
    'is'            => 'administrator',
    'protect_alias' => 'dashboard']);