簡體   English   中英

yii2拒絕用戶在后端登錄

[英]yii2 deny user login on backend

我有應用RBAC遷移的yii2高級模板。 我正在嘗試學習RBAC並遵循Docs 2.0

我已使用數據庫登錄,但前端和后端都使用任何帳戶登錄。 我已經做了2個RBAC角色(管理員,用戶),但無法理解或找到如何

限制后端登錄非管理員用戶角色。

以下是角色的代碼。 和數據庫條目:

namespace console\controllers;

use Yii;
use yii\console\Controller;

class RbacController extends Controller
{
    public function actionInit()
    {
        $auth = Yii::$app->authManager;

        // add "admin" role
        $admin = $auth->createRole('admin');
        $auth->add($admin);

        // add "user" role
        $user = $auth->createRole('user');
        $auth->add($user);

        $auth->assign($admin, 1);
    }
}

用戶表:

admin   admin@gmail.com     20  10  1421197319  1421197319
user    user@gmail.com      10  10  1421198124  1421198124

現行規則:

'rules' => [
    [
        'actions' => ['login', 'error'],
        'allow' => true,
    ],
    [
        'actions' => ['logout', 'index'],
        'allow' => true,
        'roles' => ['@'],
    ],

解決了 - 注意:解決方案不完全是RBAC而是ACF。

經過搜索和咨詢,我找到了這個yii2 viki的解決方案

我不清楚RBAC行為,因為我認為它不會讓某個角色在某些操作(登錄,提交等)之前執行特定任務。

實際上,RBAC會讓你做任何嘗試,然后檢查是否允許,如果不允許則阻止。

在一個房子里有一些庭院銷售,你可以自由地在它的前院漫游。 房門/入口前面沒有任何防護裝置,也沒有鎖定。 你試圖潛入房子,一旦你進入房子,里面有一些保安人員突然阻止你識別自己,他在房屋安全系統中掃描你的信息(數據庫中的權限),但找不到你的權利在家里。 他強迫你出局。 這個警衛是RBAC

我需要一個守衛在前門,除非他們被允許,否則他們不會讓任何人進入。 這將是ACF。

所以,現在我需要一種方法告訴后端系統特定角色不能事先執行特定操作(即拒絕后端的非管理員登錄),這對RBAC是不可能的,因此我們可以使用'matchCallback'使用ACF。

后端規則:

        'rules' => [
            [
                'actions' => ['login'],
                'allow' => true,
            ],
            [
                'actions' => ['logout', 'index'],
                'allow' => true,
                'roles' => ['@'],
                'matchCallback' => function ($rule, $action) {
                    return Yii::$app->user->identity->isAdmin;
                }
            ],
         ]

matchCallback on True允許執行操作,而False拒絕操作。 isAdmin是一個需要在User模型中定義的getter函數。

namespace /common/models/User;

const ROLE_ADMIN = 20;
public function getIsAdmin()
{
    return $this->role == self::ROLE_ADMIN;
}

我在這個yii2 viki的評論中發布了模型的完整工作代碼

你們首先登錄用戶然后檢查他的角色,沒有必要。 您的LoginForm模型具有getUser()方法,在調用load()validate()之后找到它,並使用authManager檢查角色。 像這樣的Smth:

    /** @var LoginForm $model */
    $model = Yii::createObject('loginForm');

    if ($model->load(Yii::$app->request->post()) && $model->validate()) {
        /** @var User $user */
        $user = $model->getUser();
        if (!empty($user) && Yii::$app->authManager->checkAccess($user->getId(), 'admin')) {
            // Don't validate twice
            $model->login(false);
            return $this->goBack();
        } else {
            $model->addError('email', 'This user is not authorized for administration');
        }
    }
    return $this->render('login.twig', [
        'model' => $model,
    ]);

您也不想兩次validate() LoginForm,因此將$runValidation param添加到login()方法中。

public function login($runValidation = true)
{
    if ($runValidation) {

您應該向控制器添加行為,如下所示:

public function behaviors()
{
    return [
        'access' => [
            'class' => AccessControl::className(),
            'rules' => [
                [
                    'actions' => ['create', 'delete', 'update'],
                    'allow' => true,
                    'roles' => ['admin'],
                ],
                [
                    'actions' => ['index', 'view'],
                    'allow' => true,
                    'roles' => ['user'],
                ],
            ],
        ],
    ];
}

或者這個編輯:(規則允許任何人訪問登錄但只允許管理員登錄並訪問索引頁面):

public function behaviors()
{
    return [
        'access' => [
            'class' => AccessControl::className(),
            'rules' => [
                [
                    'actions' => ['login'],
                    'allow' => true,
                    'roles' => ['?'],
                ],
                [
                    'actions' => ['index'],
                    'allow' => true,
                    'roles' => ['admin'],
                ],
            ],
        ],
    ];
}

我通過更改后端登錄操作實現了此功能。 這是我的代碼,我不知道,它是一個完美的解決方案,但它對我有用。

public function actionLogin()
{    
    if (!\Yii::$app->user->isGuest) {
        return $this->goHome();
    }

    $model = new LoginForm();
    if ($model->load(Yii::$app->request->post()) && $model->login()) {
        //check user roles, is user is Admin? 
        if (\Yii::$app->user->can('Admin'))
        {
            // yes he is Admin, so redirect page 
            return $this->goBack();
        }
        else // if he is not an Admin then what :P
        {   // put him out :P Automatically logout. 
            Yii::$app->user->logout();
            // set error on login page. 
            \Yii::$app->getSession()->setFlash('error', 'You are not authorized to login Admin\'s penal.<br /> Please use valid Username & Password.<br />Please contact Administrator for details.');
            //redirect again page to login form.
            return $this->redirect(['site/login']);
        }

    } else {
        return $this->render('login', [
            'model' => $model,
        ]);
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM