Welcome Guest, Not a member yet? Register   Sign In
Separate roles/permissions for users belonging to multiple organizations
#1

(This post was last modified: 05-28-2021, 11:59 PM by manager.)

Hello everyone. I'm going to make an app where a user can belong to multiple organizations and a user can have different roles/permissions for each organization. Currently available packages like mythauth or ionauth don't have this future. So what is the best way to implement this? what would be the best way to design database tables?
I'm thinking make table structures like this:
  • permissions (id, name, display_name)
  • roles (id, name, display_name)
  • organizations (id, name, address ...)
  • users (id, name,email, pass, created_at, updated_at, deleted_at, ...)
  • users_permissions (id, user_id, permission_id, organization_id) --- all columns except id are foreign keys
  • users_roles (id, user_id, role_id, organization_id) ---  all columns except id are foreign keys
Thanks in advance.
Reply
#2

This may help you decide, I found it very interesting. It does deal with Organizations, Roles and Permissions etc.
IDENTITY MANAGEMENT - MANAGING ROLES AND PERMISSIONS
What did you Try? What did you Get? What did you Expect?

Joined CodeIgniter Community 2009.  ( Skype: insitfx )
Reply
#3

(05-29-2021, 05:06 AM)InsiteFX Wrote: Thank you for your help.
Reply
#4

(This post was last modified: 05-30-2021, 01:44 AM by paliz.)

PHP Code:
go to https://github.com/lonnieezell/myth-auth

you need this filter it work for restful api i did change combine rule and premision auth system to father   
PHP Code:
<?php namespace CoreAuth\Filters;

use 
CoreAuth\Enums\FilterErrorType;
use 
CodeIgniter\HTTP\RequestInterface;
use 
CodeIgniter\HTTP\Response;
use 
CodeIgniter\HTTP\ResponseInterface;
use 
CodeIgniter\Filters\FilterInterface;


class 
AuthFilter implements FilterInterface
{
    public function after(RequestInterface $requestResponseInterface $response$arguments null)
    {

    }

    public function before(RequestInterface $request$arguments null)
    {

        $ruleRoute =  \CoreAuth\Config\Services::ruleRoute();

        if ($ruleRoute->ignoreRoute()) {
            return;
        }
        $response = \CodeIgniter\Config\Services::response();

        $uri uri_string();

        $authenticate = \Myth\Auth\Config\Services::authentication();
        $authorize = \Myth\Auth\Config\Services::authorization();

        $explode explode('/'$uri);

        $controller strtolower($explode[1]);

        $controllerRule $ruleRoute->getRuleAccess(explode('/'$uri)[1]);
        $permissions = array("manage-""index-""create-""update-""delete-");
        $isGroup false;
        $isAccess true;
        if (!function_exists('logged_in')) {
            //  helper('Myth\Auth\Helpers\Auth');
            helper('auth');
        }

        $current = (string)current_url(true)
            ->setHost('')
            ->setScheme('')
            ->stripQuery('token');

        // Make sure this isn't already a login route
        if (in_array((string)$current, [route_to('login'), route_to('forgot'), route_to('reset-password'), route_to('register'), route_to('activate-account')])) {

            return;
        }

        // if no user is logged in then send to the login form

        if (!$authenticate->check()) {
            return $response->setJSON(['success' => false,
                'type' => FilterErrorType::Login,
                'error' => lang('Authenticate.filter.login')])->setContentType('application/json')
                ->setStatusCode(Response::HTTP_UNAUTHORIZEDlang('Authenticate.filter.login'));
        }




        if (empty($controllerRule)) {

            return;
        }

        // Check each requested permission
        foreach ($controllerRule as $group) {
            if ($authorize->inGroup($group$authenticate->id())) {
                $isGroup true;
                // return;
            }
        }


        // $request->getMethod(false) != "get" and
        if ($isGroup == true) {

            foreach ($permissions as $item) {

                if ($authorize->permission($item "" $controller)) {
                    $isAccess $authorize->hasPermission($item "" $controller$authenticate->id());

                }

            }
        }


        if ($isGroup == true and $isAccess == true) {
            return;
        }


        if ($authenticate->silent()) {
            $redirectURL session('redirect_url') ?? '/';
            unset($_SESSION['redirect_url']);

        }

        return $response->setJSON(['success' => false,
            'type' => FilterErrorType::Permission,
            'error' => lang('Auth.notEnoughPrivilege')])->setContentType('application/json')
            ->setStatusCode(Response::HTTP_UNAUTHORIZEDlang('Auth.notEnoughPrivilege'));


    }




PHP Code:
<?php

namespace CoreAuth\Services;

class 
RuleRoute
{
    public static function getRuleAccess(string $name): ?array
    {
        $listOfRule = array(
            'profile' => null,
            'chatContact' => null,
            'chatRoom' => null,
            'chatRoomMedia' => null,
            'chatPrivate' => null,
            'chatPrivateMedia' => null,
            'dashboard' => null,
            'user' => ['admin'],
            'group' => ['admin'],
            'setting' => ['admin'],
            'visitor' => ['admin'],
            'advertisement' => ['admin'],
            'advertisementMedia' => ['admin'],
            'contact' => ['admin''coworker'],
            'contactMedia' => ['admin''coworker'],
            'newsCategory' => ['admin''coworker'],
            'newsSubCategory' => ['admin''coworker'],
            'newsPost' => ['admin''coworker'],
            'newsComment' => ['admin''coworker'],
            'newsMedia' => ['admin''coworker'],
            'viewOption' => ['admin''coworker'],
            'viewMedia' => ['admin''coworker']);

        foreach ($listOfRule as $key => $value) {
            if ($key == $name) {
                return $value;
            }
        }
        return null;
    }

    public static function ignoreRoute()
    {
        $listOfIgnore = array('home''test''auth');

        foreach ($listOfIgnore as $item) {
            if (preg_match("~\b" $item "\b~"uri_string())) {
                return true;
            }
        }

        return false;
    }


Enlightenment  Is  Freedom
Reply
#5

i forgot got that toooooooooooo


<?php namespace CoreAuth\Config;


use Config\Services as BaseService;
use CoreAuth\Services\RuleRoute;

class Services extends BaseService
{



public static function ruleRoute($getShared = true)
{
if ($getShared)
{
return static::getSharedInstance('ruleRoute');
}

return new RuleRoute();
}

public static function jwtSecretKey()
{
return 'sljjljtgidhvxvxzfdfarwfsdkk_ayuikjukliebmvlhqewhw';
}
}
Enlightenment  Is  Freedom
Reply
#6

I’m not sure what the difference is between an “organization” and a “group”. Myth:Auth has full support for groups and group-based roles and permissions.
Reply
#7

I also thought that the groups in Myth/Auth would do the same thing.
What did you Try? What did you Get? What did you Expect?

Joined CodeIgniter Community 2009.  ( Skype: insitfx )
Reply
#8

(This post was last modified: 05-30-2021, 06:40 AM by paliz.)

Obky boys

My filter is ablittle tricky
First is there any rule or not
If have role dose have any premission base on reatfull


Setting ctl

Should be admin then and also has a premission for user not for group okay

I think like that

I use it like that

I forgot something

If admin and coworker got setting ctl

Cowoker can only vist setting ctl but admin base on premission group or user could deffrent

If user presmission setting. Manga. Mean user can do curd
Base in http request put put delete.

Or group like exmple i told


Or cowork only have premission group for edit. Put http

Sound crazy but it work

The idea is supper sample

I use both aystem rule and premission to gather in this filter and dont apply code any where

One filter for auth

Heres another one

Cowork setting ctl only get request

Admin with id 1 can do put get delete post request

Other admin can do get or put request



See its felexable
Enlightenment  Is  Freedom
Reply
#9

this filter work for ctl user access and permission base on http request

<?php namespace CoreAuth\Filters;

use CoreAuth\Enums\FilterErrorType;
use CodeIgniter\HTTP\RequestInterface;
use CodeIgniter\HTTP\Response;
use CodeIgniter\HTTP\ResponseInterface;
use CodeIgniter\Filters\FilterInterface;


class AuthFilter implements FilterInterface
{
public function after(RequestInterface $request, ResponseInterface $response, $arguments = null)
{

}

public function before(RequestInterface $request, $arguments = null)
{

$ruleRoute = \CoreAuth\Config\Services::ruleRoute();

if ($ruleRoute->ignoreRoute()) {
return;
}
$response = \CodeIgniter\Config\Services::response();

$uri = uri_string();

$authenticate = \Myth\Auth\Config\Services::authentication();
$authorize = \Myth\Auth\Config\Services::authorization();

$explode = explode('/', $uri);

$controller = strtolower($explode[1]);

$controllerRule = $ruleRoute->getRuleAccess(explode('/', $uri)[1]);

$isGroup = false;
$isAccess = false;
$counterPermission = 0;
if (!function_exists('logged_in')) {
// helper('Myth\Auth\Helpers\Auth');
helper('auth');
}

$current = (string)current_url(true)
->setHost('')
->setScheme('')
->stripQuery('token');

// Make sure this isn't already a login route
if (in_array((string)$current, [route_to('login'), route_to('forgot'), route_to('reset-password'), route_to('register'), route_to('activate-account')])) {

return;
}

// if no user is logged in then send to the login form

if (!$authenticate->check()) {
return $response->setJSON(['success' => false,
'type' => FilterErrorType::Login,
'error' => lang('Authenticate.filter.login')])->setContentType('application/json')
->setStatusCode(Response::HTTP_UNAUTHORIZED, lang('Authenticate.filter.login'));
}


if (empty($controllerRule)) {

return;
}

// Check each requested permission
foreach ($controllerRule as $group) {
if ($authorize->inGroup($group, $authenticate->id())) {
$isGroup = true;
// return;
}
}


$method = strtolower($_SERVER['REQUEST_METHOD']);
// permission by http request post put delete
$permissions = permissionMethod($method);

if ($isGroup == true && !empty($permissions)) {

foreach ($permissions as $item) {

if ($authorize->permission($controller . "" . $item)) {
$counterPermission++;
if ($authorize->hasPermission($controller . "" . $item, $authenticate->id())) {
$isAccess = true;
break;
}
}

}
}
// it get request dont need any permission
//or dont have permission in database for http request
if (empty($permissions) || $counterPermission == 0) {


$isAccess = true;
}


if ($isGroup == true and $isAccess == true) {
return;
}


if ($authenticate->silent()) {
$redirectURL = session('redirect_url') ?? '/';
unset($_SESSION['redirect_url']);
}

return $response->setJSON(['success' => false,
'type' => FilterErrorType:Tongueermission,
'error' => lang('Auth.notEnoughPrivilege')])->setContentType('application/json')
->setStatusCode(Response::HTTP_UNAUTHORIZED, lang('Auth.notEnoughPrivilege'));


}


}

put this function in auth_helper.php in help folder


if (!function_exists('permissionMethod')) {
/**
* return permission by http request put post delete
* @param string $method
*
* @return array
*/
function permissionMethod(string $method): array
{

switch ($method) {

case "post":
return ["-post-put-delete", "-post-put", "-post-delete", "-post"];
case "put":
return ["-post-put-delete", "-post-put", "-put-delete", "-put"];
case "delete":
return ["-post-put-delete", "-put-delete", "-post-delete", "-delete"];
default:
return [];
}


}


}
Enlightenment  Is  Freedom
Reply
#10

(This post was last modified: 06-04-2021, 04:01 AM by manager.)

(05-30-2021, 05:32 AM)MGatner Wrote: I’m not sure what the difference is between an “organization” and a “group”. Myth:Auth has full support for groups and group-based roles and permissions.
By 'organization' i mean 'company'.  

Let's say we have an app for managing invoices of legal entities. 
Users in real life can work for several companies at the same time. So user Bob works in "Company A" and "Company B". Both companies use our invoicing app. 

The question is how to handle situation when user Bob has "single account in our invoicing app" , but must have different permissions in our app granted by companies where he works ?
Lets say in "Company A" Bob has "permission1, permission2", but in "Company B" have only "permission 3". 
How to handle all this above situations in our database tables structure and in our auth module ?
Reply




Theme © iAndrew 2016 - Forum software by © MyBB