Decouple user information and authentication information in Symfony - php

First off, I am new to Symfony, so I don't know the exact functionality of bundles like FOSUserBundle etc., as well as the terminology.
I am looking for a way to use the Symfony security component in a way that enables me to decouple a user's login credentials (say, a login name and a password, maybe the roles) from the actual user meta data (like first name, last name, groups, birth date, etc.).
The idea is that a user can login with different sets of login name/password and still be recognized as the same user (in the end that means, getting the same User object).
To me, this comes especially handy in combination with multiple authentication providers. For example, if I wanted to enable my users to login via an OAuth2 service as an alternative to logging in with their locally-hosted login name/password-combination (like StackExchange does, for instance), how would I do that?
I have read multiple pages of documentation of Symfony, e.g.:
https://symfony.com/doc/current/security.html
https://symfony.com/doc/current/security/entity_provider.html#create-your-user-entity
This latter one even says at 1) Create your User Entity, that a password is a field of User.

I have recently created just that, first I named my classes UserCredentials and UserDitails and because of the confusion of the getUser function i decided to rename UserCredentials to User. I agree with Alex Blex about the relation (manyToOne on the User side). When you decouple your login and metadata you will need to learn how to embed forms or creating your own form models, which is something I am currently working on and you might need to implement callback functions for deleting and updating entities. The more I work on my UserBundle, the more it looks like the FOSUserBundle. There is quite a bit of work of designing it to work well but it's great for learning. If you wish to inspect how the FOSUserBundle works, after you install it, you can find it in the vendor/friendsOfSymfony folder, it might provide a few answers.

Related

How do you setup permission/views/routes for different user roles?

I am building a eCommerce platform. Where I have to make several user roles and specific permission for them. I have successfully created admin and default user roles and permission.
But I am getting so much trouble to show the views and menu items based on other user roles like Editor/Manager/CS Team.
I tried to do using different middleware for every one of them. But It's not working efficiently and even at all.
For the Admin role, I created a Admin Middleware where I am checking user role type and giving access. I defined the admin middleware on Route gruop.
Can you suggest me? - how to setup permission/views/menu items efficiently for different user roles?
Thanks in Advance.
Note: I am trying to do it without any package.
Yes you can make your own custom build library by setting roles,permission table in database and as soon as the user log's in you put all that information in session or cache. But doing so might get you in trouble in future coz lack of testing it's all feature, You have to be sure what exactly you are doing to manage it by yourself or else you can use already tested many time library like
laravel-permission
Using a well known and trusted library ensures that it will solve your problem, but take your time to read it's documentation and analyse if it contains all features that you want in your application.
You need to define policy.
Policies are a great way to protect actions on your Eloquent Model. Laravel Policies are the part of Laravel Authorization that helps you to protect resources from unauthorized access.
Please refer this documentation to how to register policy and how it works in views file:
https://www.larashout.com/laravel-policies-controlling-authorization-in-laravel

Symfony 1.4 Different CRUDs for different roles

I want to provide specified actions for different role in Symfony 1.4 project.
Project contains several database tables which values can be modified only by certain roles.
For example, an administrator gains access to CRUDs for all models.
Another role (let it be a consultant) can only retrieve (not modify or remove) results from specified models (not all).
How can I support such a feature in symfony?
I assume that roles for the project will be specified in advance.
One solution I was thinking about is creating modules and actions for each role separately (crud panels + one logging interface), but it sounds like a huge job.
Just wondering what the smarter way is.
I think the best way to achieve that is definitively credentials (it is for sf1.2 but ok for 1.4).
I recommend you to use sfGuardDoctrine to use some groups with associated permissions (which are credentials). You define a group admin, consultant, etc .. You associate some credentials, like modifiy, remove, create, edit, etc ..
And then, every time a user will log in, it will automatically have defined credentials (associated to him or by his group).
After, you have to check for every action if the user has can perform it:
if($this->getUser()->hasCredential('modify'))
{
// authorized action
}
Here is some more documentation for sfGuard (related to sf1.0 but it is good to understand how it works).

Creating a User Login System: Put logic in Code or Database

I am trying to create a login system thats generic so that it can be adapted for use in various apps. I decided that 2 main "parts" of the system will be User Meta Data & Roles/Resources/ACL.
1. Metadata
I thought of keeping most data like what meta data are available for users in the database, so that admins can manage them using some GUI.
Problem is how can I then configue how I want inputs to render (textbox, checkbox, radios etc.). Then another problem is validation, filters.
2. ACL
I think for simple ACL it will work fine. But suppose I want say users to be able to modify posts they own. In Zend_ACL that is accomplished with Assertions. I thought that will make a "simple" login system overlly complex? Also it will be hard to build I suppose?
Currently I have my database like
Logging in users: I recommend using a separate controller (call it Auth for instance) that has loginAction and logoutAction. Zend_Auth (Zend_Auth using database) will check the database for the right credentials. Once the user is verified, you will save it in the global accessible place(the Zend_Auth class has methods to do this). This is also a good moment to query which roles the user has and store them.
Metadata part of your application: I'm not sure what the question is exactly but I assume you want to store dynamic information about user and have a GUI for admins to manage this. Why you would render different types of controls? Validating the information can be done by defining a lot of the most common metadata (like Twitter) and create rules for them. In the save action for the metadata you would validate using these rules.
ACL: Resources rarely change, you are better off putting them in a configuration file (for speed). You should give a lot thought to resources: what are they exactly to you? Controllers? Modules? Create a plugin that will preDispatch every request checking the role of the logged in user against the requested resource. E.g.:
$action = $request->getActionName();
$controller = $request->getControllerName();
// role, resource, privilage
if (!$acl->isAllowed($user->role, $controller, $action) {
//go to access denied page!
}
Now that Zend_ACL is used for the global access rules, you are better off checking for specific access inside the action itself (like if ($loggedInUser == $article->author) {//edit the article};).
Also don't forget Zend_ACL can be integrated with Zend_Navigation to hide menu items users are not allowed to use (and more).

CodeIgniter authentication + user privileges

I'm trying to build an authentication system in my application, but I'm having some problems in deciding which is the best way I could acomplish what I want in CodeIgniter.
The website allows companies to manage their buildings. A company can have many buildings, and many users (when I say users I mean employees from that company).
In this website I would like two have (basically) four general kind of users.
Super Admin: This would be able to add new admins and new companies to the database, and give privileges to the rest of the admins.
Admin: This would be able to do different stuff depending on the assigned privileges.
Company Super User: This user would be created directly when an admin creates a new company. This user would be able to create new users for that company, and since s/he would have total permissions, he would be able to do everything that the other users can do.
Company User: Depending on the privileges assigned by its super user, this user would be able to do and see different data (for example, a simple user would just be able to see information from one of the many company buildings).
So, even though I've seen many authentication libraries out there for CodeIgniter, it would be nice to hear any recommendations about how I could design this "authentication role based" system, and if you particularly recommend a library that could help to accomplish this.
Appreciate!
There Are many libraries that already handle Authentication within Codeigniter, but the one I would recommend is Ion_Auth. It handles user permissions (groups) very well and I've actually done a detailed writeup outlining a good way to handle this situation with Ion_Auth.
I suggest FlexiAuth library which is a re-modified version of ion Auth, and has lot of features already built in, simply out of the box.
I've been developing a role based authentication system for Codeigniter called WolfAuth, here's the repository. It's still early days, but it sort of works. You can add roles, etc and then restrict functions and classes to particular user roles and usernames.
Use CI_aauth. I like this, this is very good from others auth.
https://github.com/kabircse/CodeIgniter-Aauth

custom controller name in CakePHP

I am developing an application in cakephp, I have to provide a user page for each user in the site like www.example.com/username, username will changes for each user, when a visitor comes to this url he gets details of the user with that particular username, but in cake username tries to get the controller with that name, How can I done this ?
My first response would be to say "don't do that". What happens if you decide to add a promotions page at some point in the future but you've already got a user named "promotions" or you want to add a forum system but you've already got not-very-nice users named "forums" and "boards"?
Better to do something like www.example.com/users/username. (eg. www.example.com/users/ssokolow) That's how all the sane sites do it. In fact, on a related note, Mozilla just redesigned the addon collections system so that collection names are namespaced under the usernames to solve a similar issue.
Anyway, whatever you decide, instructions for customizing your URL mappings independently of your controller designs are in Section 3.4.5: Routes Configuration in the CakePHP 1.3 manual.
You'll want to set up the order of precedence so that CakePHP tries everything else first (like the login page and the submit handlers for forms accepting user data) and then tries your username mappings as the last thing before giving up and returning a 404.
You'll still have to manually maintain a list of usernames that are banned because their profile URLs would be overridden by site-global stuff (eg. login) and you'll still have to watch out for cases which malicious users might be able to exploit to trick other users into something, but it will work.
You can do it with routes as a fallthrough at the end of the routes file, but it's not advisable - ssokolow has explained why. I have used something very similar for a CMS, but for pages rather than users and uniqueness was maintained by the system.
If it's essential that the URL reads like www.example.com/username rather than www.example.com/users/username then I would look at doing it by apache rewriting the url. This will probably still give you problems if a username coincides with a pagename and may well be confusing for visitors not to mention search engines.
Keep it simple - don't give yourself a headache.
It's a nice feature for users to access their accounts in this way and, contrary to other answers, I don't think it's a headache or undesirable in any way.
The best way to achieve this is with routes, but not manually - database driven routes. Mark Story has a great article on the topic and I've used this approach with great ease and success on very large websites:
http://mark-story.com/posts/view/using-custom-route-classes-in-cakephp
The only change I make is that I maintain a table called "routes" and have a corresponding Route model. The routes table simply has id/name/value fields. The name is the nice URL (in your case "somegreatuser"), whilst the value is the system URL (e.g. users/view/123).
All you need to do is maintain a blacklist of reserved usernames which is easily done using validation in the Route model.

Categories