Difference between #2 and #4 of
[Guide] How to actually separate Frontend (User) and Backend (Admin) on Yii2 Advanced

Changes

Title unchanged

[Guide] How to actually separate Frontend (User) and Backend (Admin) on Yii2 Advanced

Category unchanged

How-tos

Yii version unchanged

Tags unchanged

yii2, user, auth, cookie, session, request, different, separate, backend, frontend, app, advanced, domain, login, autologin, CSRF, temp, cache, admin, user, member, system

Content changed

#[Guide] How to actually separate Frontend and Backend on Yii2 Advanced#
 
 
---
 
 
I am writing this guide because I struggled to find a resource that included ALL of the necessary steps to completely separate the frontend from the backend. After reading guides like [Configuring different sessions for backend and frontend in yii-advanced-app](http://www.yiiframework.com/wiki/686/configuring-different-sessions-for-backend-and-frontend-in-yii-advanced-app/) and [yii2 configuring different sessions for backend and frontend in yii advanced application template](http://www.yiiframework.com/wiki/767/yii2-configuring-different-sessions-for-backend-and-frontend-in-yii-advanced-application-template/), there are still steps missing. It is funny how the 2nd one says it is an extension of the first one's article. So I guess, my wiki guide here is yet a 3rd and more complete extension of both of them. I also found a few StackOverflow questions and blog posts regarding this topic. None of them fully worked, and must be missing some magic sauce! ####Tip####
 
> Tip: For testing, use another browser and it's private browsing feature. I use Chrome as my default browser, and during testing I open Firefox in private browsing mode. This way, I can close the browser and all cookies are gone. I don't have to worry about clearing history, cache, cookies, etc. #### Problem####
 
Say you have a 'user' table for frontend and you want an 'admin' table for backend. You think you just have to duplicate /common/models/User.php and name it Admin.php, and change /common/models/LoginForm.php to AdminLoginForm, and update the references to them in the backend. Seems logical, and is only the beginning. What will happen is you login to frontend, then open a new tab and go to backend, you will be logged in as a member from the 'admin' table matching the same ID. User ID 3 will have you logged in as Admin ID 3 in the backend. If you click logout in either of them, you get logged out of both.. You get weird behaviour and it just isn't right. Now obviously, we can't have users login to the frontend and be able to manually navigate to /backend and be logged in. After following the two guides I mentioned earlier, it still didn't work right. I was able to login individually, but the logout of the frontend gave a "400 Bad Request" error. I read that someone changed the POST of the logout to GET. That is absolutely not necessary, a bad idea, and just is not the *correct* or proper solution. The reason the logout gave a 400 error, was because of invalid CSRF parameters. ---
 
 
## The Proper Solution##
 

I am not going to walk you through installing or setting up the Yii2 Advanced Template. The docs already cover that [here](http://www.yiiframework.com/doc-2.0/guide-tutorial-advanced-app.html). So I am assuming you know how to install it and create the user table.
[...]
Duplicate `/common/models/User.php` and name it `Admin.php`. Open it up, and change the name of the class from 'User' to 'Admin'. You also need to change the `tableName()` function to `return '{{%admin}}'`.

###
# Truncated example of /common/models/Admin.php:####
 
 
    

 
 
 
```php 
class Admin extends ActiveRecord implements IdentityInterface     {      public static function tableName()      {     return '{{%admin}}';     }
 
    }
}
 
}
 
```
Duplicate `/common/models/LoginForm.php` and name it `AdminLoginForm.php`. Open it up, and change the name of the class from 'LoginForm' to 'AdminLoginForm'. At the bottom of the class, there is the `getUser()` function. It references the User class. Change `User::findByUsername($this->username)` to `Admin::findByUsername($this->username)`. Save the file. #### Truncated example of /common/models/AdminLoginForm.php:####
 
 
    

 
 
 
```php 
class AdminLoginForm extends Model     {
 
    
{
 
public function getUser()     {
 
    
{
 
if ($this->_user === false) {     $this->_user = Admin::findByUsername($this->username);     }      return $this->_user;     }
 
    }
 
}
 
}
 
```
Now you need to update `/backend/controllers/SiteController.php` to use these new models. You need to change all references of 'User' to 'Admin' and 'LoginForm' to 'AdminLoginForm', in the namespaces and the code! #### Truncated example of /backend/controllers/SiteController.php:####
 
 
    

 
 
 
```php 
namespace backend\controllers;

use Yii;
[...]
}
}
}
 
```


This was common sense for me. Since the backed didn't have it's own login form or model, I knew I needed to make an Admin model to use the 'admin' table in the database, and AdminLoginForm to use that Admin model (ie: Admin::findByUsername() ).
[...]
What wasn't clear, was what to do after that. There are issues with the cookies, session, and CSRF values. If we don't manually specify them in the config, then they try to use the same ones for both frontend and backend. That is why you see the weird behaviour, like being logged into both sides after logging into only one of them and getting an error when you try to logout. So let's setup the config.

To be honest, the Yii documentation is lacking, and skims over the advanced template.
Don't get me wrong, they wrote a lot and put a lot of effort into the docs that they do have. I just feel that the extra stuff isn't as greatly covered. Hopefully, it continues to grow and gives us more info on the extra stuff. Right now I feel I just have to Google what I need and hope someone else has already covered it.
 
 
These issues have nothing to do with programming knowledge, I have been programming for a long time and in many languages.. This has to do with just understanding Yii2. So don't get frustrated :) In `frontend/config/main.php` you need to edit the 'user' component, and add 'session' and 'request' to the list. #### Truncated example of /frontend/config/main.php:####
 
 
    

 
 
 
```php 
'components' => [
'user' => [
'identityClass' => 'common\models\User',
[...]
'csrfParam' => '_frontendCSRF',
],
],
 
```


**YOU MUST REPLACE [RANDOM KEY HERE] WITH A REAL RANDOM KEY!**
[...]
For the backend, it's the same thing, only we need unique values and to specify the `common/models/Admin.php` model.

###
# Truncated example of /backend/config/main.php:####
 
 
    

 
 
 
```php 
'components' => [
'user' => [
'identityClass' => 'common\models\Admin',
[...]
'csrfParam' => '_backendCSRF',
],
],
 
```


Again, use [Random.org Random String Generator](https://www.random.org/strings/) to generate the `cookieValidationKey`. **DO NOT** use the same key you generated for the frontend! You can see, the user 'identityClass' references the Admin model. Also notice the refences to backend.
[...]
As long as you use different values for these, you can have as many differnet systems as you want. You could copy the "frontend" folder, and have admin, staff, members, billing, support, forum, blog. As long as you change the values to be unique in the main config of each one, you can create as many as you need. You would just need to create an alias for each one of them.

##
## The End :)#### That's it. Now your frontend and backend are completely separate. You can login to each and not have clashes with the other, or worry about other's being able to access it when they shouldn't. This is not a chincy hack, and the most proper way to do it that I have found. #### Credits#### I want give special thanks to [Serge Postrash @SDKiller](https://github.com/SDKiller). Thanks again for helping me with the config values I was missing.
9 1
18 followers
Viewed: 119 986 times
Version: 2.0
Category: How-tos
Written by: Wade Shuler
Last updated by: samdark
Created on: May 8, 2015
Last updated: 9 years ago
Update Article

Revisions

View all history