Background: Building a web app (as an introduction to CakePHP) which allows users to manage a lounge. A lounge is composed of a blog, contacts, calendar, etc. Each lounge is associated with a subdomain (so jcotton.lounger.local would take you to my lounge). The root of the site, used for creating new lounges, registering users, etc is hosted on lounger.local. I am using Cake 2.0.
Questions:
I wanted to be able to separate actions and views associated with the root site (lounger.local) from individual lounges (subdomains of lounger.local). After a good deal of research I settled on the following soln. I setup a prefix route "lounge" and added the the following code in routes.php. Actions (and views) associated with a lounge all contain the prefix lounge (ex: lounge_index()). How would you handle this?
if(preg_match('/^([^.]+)\.lounger\.local$/',env("HTTP_HOST"),$matches)){ $prefix = "lounge"; Router::connect('/', array('controller' => 'loungememberships','action' => 'index', 'prefix' => $prefix, $prefix => true)); /* Not currently using plugins Router::connect("/:plugin/:controller", array('action' => 'index', 'prefix' => $prefix, $prefix => true)); Router::connect("/:plugin/:controller/:action/*", array('prefix' => $prefix, $prefix => true)); */ Router::connect("/:controller", array('action' => 'index', 'prefix' => $prefix, $prefix => true)); Router::connect("/:controller/:action/*", array('prefix' => $prefix, $prefix => true)); unset($prefix); }
Each time a user performs an action within a lounge such as posting a comment within the blog, adding a contact, etc, it is necessary to lookup the lounge_id (based on the subdomain); this is necessary to verify the user is authorized to perform that action and to associate the corresponding data with the correct lounge. I have implemented this via the beforeFilter function in AppController. Each time a request is received with a subdomain a search is performed and the lounge_id is written to a session variable. Each controller then loads CakeSession and reads the corresponding lounge_id. Is this better than calling ClassRegistry::Init('Lounge') and doing the lookup in each controller? Is there a better soln?
Thanks in advance for the help
The way I approached this was with a custom route, and some trickery with route configuration similar to your example.
First, I have a "Master domain" that is redirected to and used as the main domain for the multi-tenancy site. I also store a default action i want them to take. I store these in configuration variables:
Next, I created a
DomainRoute
route class in/Lib/Route/DomainRoute.php
:This custom route class is used within the
/Config/routes.php
file to setup multi-tenancy.On inspection of the custom router, you will see that I am pulling the current domain being accessed and adding that to the
$params
array.While this does not directly achieve what you are after, minor modifications will get you on the right track with your requirements. There is not a great deal of information about Custom Routes, but here is the CakePHP documentation link for custom route classes.
I hope that helps!