I have a bit of a stumper that I am hoping someone has a fresh idea on.
The Problem:
I have a client that owns 3 domains all selling similar products. The domains are all very interlinked together for various SEO purposes. I need to be able to have a single cart (session data) exist on all 3 domains and display data regarding that cart on all three. The info to display basically includes a synopsis of their cart. I have full control over a VPS server environment from which all three domains reside. Furthermore all three domains server up the same index.php file from the same directory. The index file then parses the url string to deliver the proper content. The main advantage to this is that the session save path remains the same (big bonus I found). Because the session save path is accessible from all three domains all I really need to pass from one domain to another is the session id.
I have tried a number of solutions and each has fallen slightly short of what I need. Based on various searches around the web here is what I have tried.
Prepend each link on the site with the session id:
This solution is the most widely posted through the web it looks something like this
<? $sessionid=session_id();?>
<a href="http://example.com/page?sessionid=<? echo $sessionid;?>">Link</a>
then on the accepting page you use something like
<? $sessionid=$_GET['sessionid'];
session_is($sessionid);
session_start();
?>
This works but has a very open security issue as all someone has to do to hijack a session is put in a sessionid= at the end of any url on my site. Note I could use session_destroy() when the user is done with their visit but that is still not secure there is no clear way to determine when a user leaves permanently. No matter how you close the session it is still vulnerable.
Initiate a session across all domains at once
This solution uses a specified file on domain2 that is accessed by domain1 and again passes the session var. There are 2 variations I found on this.
Variation 1 : using cURL
from domain1 you curl a file on domain2 passing in the sessionid from domain1. domain2 takes in this session id and assigns it for the domain. the code looks something like
<?
//page on domain 1 does this
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, "http://domain2.com/index.php?sessionid=" . session_id());
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$temp = curl_exec($ch);
curl_close($ch);
unset ($temp);
?>
then on domain 2 we would have
<? $sessionid=$_GET['sessionid'];
session_is($sessionid);
session_start();
?>
So this worked in some browsers but not in others. firefox yes, explorer no
Variation 2 : using an image link
very similar to the first variation but in this case you use an image tag. this is less secure because upon viewing the code a hacker could see the method being used and again hijack the session. regardless the solution looks like this
<img src="domain1.com/session_setter.php?sessionid=<? echo session_id();?>" height="1" width="1" />
then the same script exists on domain2 as above
<? $sessionid=$_GET['sessionid'];
session_is($sessionid);
session_start();
?>
this works in firefox but not in IE
Maintain a DB of sessions
This is the best solution I have come up with but still has limitations. Basically the user is uniquely(sort of) identified in a db using their IP and User Agent. When they visit any page of the site their IP is cross referenced with the db to see if they have a session already started. If they do the session is re-implemented and everything works as it should. The code looks like this.
<?
$result=mysql_query("SELECT sessionid FROM sessions WHERE ip='".$_SERVER['REMOTE_ADDR']."' AND time>'".(time()-(24*60*60))."' AND agent='".$_SERVER['HTTP_USER_AGENT']."' AND closed='0' ORDER BY time DESC LIMIT 1");
if (mysql_num_rows($result)>0){
$session=mysql_fetch_assoc($result);
session_id($session['sessionid']);
}
session_start();
$time=time();
if(isset($session['sessionid'])){
mysql_query("UPDATE sessions SET time='$time' WHERE sessionid='".$session['sessionid']."'");
}
else{
$agent=$_SERVER['HTTP_USER_AGENT'];
$ip=$_SERVER['REMOTE_ADDR'];
$sessionid=session_id();
mysql_query("INSERT INTO sessions SET sessionid='$sessionid', ip='$ip',agent='$agent', time='$time'");
}
?>
Note: half of this is done at the top of the page the other half at the bottom.(doesn't make too big a difference but...)
OK so this work great except, 2 users on the same sub-network will have the same IP. If they happen to use the same type of machine and browser usera and userb will have the same session.
While this problem will not be run into regularly it still can happen. My main concern is the customer service department for this website. All the CS agents are likely on a similar computer managed by a single IT dept that updates everything at the same time. Thus everyone in that office will use the same IP and the same User agent.
If anyone has an idea or solution on this that I haven't tried please let me know. At this point I am open to just about anything. I think all I really need is a truly unique identifier for each users machine combined with the last solution would be perfect.