0

I'm developping a webapplication in Symfony2. The website is supposed to have a database per client. My idea was to make a main database with information about all organizations and their databases. But now I'm running into some trouble.

Every client has their own users. This information should be stored in their own database. So in my opinion every client should have their own login page. Now I started by adding a prefix to see what client you are : example.com/{client}/ -> controllers .. The thing is you're not allowed to set a parameter in your route for a login page in symfony! So how should I make sure every client has a different login page?

Another thing is security. What is the best way to make sure a user cannot change the route parameter to a different client and get access?

I've been looking for guides on the internet to do what I need to do. But I can't find any solid ways for Symfony2 .. Mostly it's half solutions, for example just switching between the databases via a service. If there is another php framework that does all this much better I would definately consider changing to that too.

I hope you guys can give me some advice. Thanks in advance.

Matthias
  • 330
  • 3
  • 7
  • 20
  • 1
    I thin this will help you much: http://stackoverflow.com/a/9291896/3675759 – malcolm Aug 20 '15 at 11:36
  • This doesn't really help, I already know how to switch the databases. The problem is with loging in and making sure the site is secure using variable prefixes .. – Matthias Aug 20 '15 at 12:07
  • Then you must have many firewalls. – malcolm Aug 20 '15 at 12:20
  • You not going to have much luck trying to select completely different databases based on routing. There is all kinds of caching going on and by the time you get to the route section it's too late. For a small number of clients, setup one app per client. Otherwise you need a combined database. – Cerad Aug 20 '15 at 12:32
  • These separate databases have the exact same schema but with their own data? Can you elaborate on the purpose of having a separate database? – Z-WolF Aug 21 '15 at 11:31
  • @Z-WolF checkout multi-instance database architecture – some_groceries Aug 21 '15 at 13:01

2 Answers2

0

what you have is a multi instance database structure where each client has their own seperate database, how about using a multi tennant db structures where all clients are stored in one single db and website setup is done based on client id, that way no need for a seperate login page or database switching. if this is not a huge and significant change in project structure you could consider it. would be cheaper too

if its impossible to change the project structure, then how about using subdomains instead of url slugs company.example.com in place of example.com/company

some_groceries
  • 1,164
  • 18
  • 38
  • Our client really wants to have seperate databases because of sensitive information so .. How exactly will subdomains be more useful than the url slugs? – Matthias Aug 20 '15 at 13:10
  • i would't say subdomains are more useful, you said that symfony does not allow parameters to be set at the login page route, so this a way to avoid it. client1.example.com/login would look inside client1's database and find its users client2.example.com/login would look inside client2's database... – some_groceries Aug 20 '15 at 13:18
  • Ok but say a user is logged in at client1.example.com. He changes the url to client2.example.com .. then I have to make sure he cannot access this. Symfony uses the firewall system for this, but I can't use variables in the firewall. So how can I solve this? I can't hardcode everything .. – Matthias Aug 20 '15 at 13:25
  • if the user changes the url to client2.example.com/login then he would have to know the password of client2 so what's the problem there? he would not be able to login with his password :) – some_groceries Aug 20 '15 at 13:27
  • And do you think a users login information should be all in the main database or in their organizations database? – Matthias Aug 20 '15 at 14:14
  • it depends on the rest of the project, you have to ask yourself how the login information is related to data already present in the main database, what advantage you would have in centralizing your login, what would be the drawbacks, if i had to decide without the knowledge of the structure then i would have login info seperately inside each organization's db, reason - what if a single client wanted to change the way he logged in, then it would change for all the other clients too, which is a terrible situation to be in – some_groceries Aug 21 '15 at 06:28
-1

As i see it you got 2 options for the

checkout multi-instance database architecture

(something like the "cloud" option i assume?)

1: Use a subdomain for each client where you deploy a different app oriented to manage that database, whereas on your main app, generate the directory structure, deploy the symfony app and manage the vhost and dns zone generation.

2: For the sake of this explanation we'll use this:

Clients = each client owner of a database.

Users = client's clients.

Every client uses the same user entity.

You mentioned that you know how to switch databases, then in your database store your clients info including the database credentials (user, pass, db, etc..) and store the users info on the database of their respective client. Now when you call example.com/{client} you look in your db for that {client} load the database info for that client, switch the database and let the user login and do his/her thing. Obviously on subsequent requests is better if you store the database credentials on the session.

Now you must be asking: Q: what if the user changes the {client} after they login? A: symfony logs out the user.

or at least that is what the documentation says.

Once the user is logged in, the entire User object is serialized into the session. On the next request, the User object is deserialized. Then, the value of the id property is used to re-query for a fresh User object from the database. Finally, the fresh User object is compared to the deserialized User object to make sure that they represent the same user. For example, if the username on the 2 User objects doesn't match for some reason, then the user will be logged out for security reasons.

Q: But what if the user has the same user/pass on the other {client}? A: remember that also the id is serialized but if you also want to add another layer of security, just add a field in the user entity where it references to what client it belongs (inside their own database) and serialize it.

Z-WolF
  • 399
  • 1
  • 8