这将是一个漫长的...
由于Cookie管理错误,我遇到了错误的登录失败错误。首先,我正在管理一家封闭式商店(B2B),客户必须先在其中登录才能看到目录。每个未注册的访问都将重定向到登录页面,但是有时,即使用户名和密码正确,客户也无法登录。我说“用户名”是因为我使用Diglin_Username扩展名和StoreRestricition插件来实现所需的行为。发生的是,有时我发现Magento留下了两组不同的Cookie,它们分别指向两个不同的域(例如,.www.abc.com和.abc.com)。
看完这篇文章早期会话实例从大艾伦风暴,并在浏览器中发现了可怕的PHPSESSID饼干我研究了一些深入的问题。
我发现是两方面的。首先,我在Mage_Core_Model_Session_Abstract_Varien类的函数start()中放置了一个Mage :: Log()调用,以记录Magento发起新会话的各种尝试,并注意到在第一次Mage :: run()调用preDispatch()之后Mage_Core_Controller_Front_Action类的,dispatch()和postDispatch()方法以通常的顺序被调用,但是似乎在postDispatch()执行时找不到由preDispatch()启动的会话,而是继续创建新会话。为此,我发现Magento 1.7.x和1.8.x版本之间的代码有所不同,我认为可以解决这个问题:
Magento 1.7.x-Mage_Core_Model_Session_Abstract_Varien类:
public function start($sessionName=null)
{
if (isset($_SESSION)) {
return $this;
}
.
.
}
Magento 1.8.x-Mage_Core_Model_Session_Abstract_Varien类:
public function start($sessionName=null)
{
if (isset($_SESSION) && !$this->getSkipEmptySessionCheck()) {
return $this;
}
.
.
}
我只是找不到在哪里设置SkipEmptySessionCheck属性,因此我最终以这种方式修补了Mage_Core_Controller_Front_Action类:
public function postDispatch()
{
parent::postDispatch();
if (!$this->getFlag('', self::FLAG_NO_START_SESSION )) {
if (session_id()) {
Mage::getSingleton('core/session')->setLastUrl(Mage::getUrl('*/*/*', array('_current'=>true)));
}
}
return $this;
}
如果找不到无法启动的会话,则postDispatch()不会调用Mage :: getSingleton('core / session')(这将创建一个新会话)。对PHPSESSID cookie如此之久,一切都完成了,我想...
但事实并非如此。现在,我摆脱了PHPSESSID cookie,但仍然转到浏览器中保存的两个不同的cookie组(通常)。仅删除我可以成功登录的错误cookie,否则,即使没有消息,我也被重定向到登录页面。我试图在系统配置中明确声明cookie域,但这不能解决问题。
再次深入代码库,我发现在Magento设置cookie的各个地方,它使用Mage_Core_Model_Cookie类中的getDomain()函数来使用域:
public function getDomain()
{
$domain = $this->getConfigDomain();
if (empty($domain)) {
$domain = $this->_getRequest()->getHttpHost();
}
return $domain;
}
现在,如果您在浏览器中查看从Magento获得的页面,则可以在“标题”部分中找到以下内容:
<script type="text/javascript">
//<![CDATA[
Mage.Cookies.path = '/';
Mage.Cookies.domain = '.www.abc.com';
//]]>
</script>
这些行来自app / design / frontend / base / default / template / page / js / cookie.phtml:
<script type="text/javascript">
//<![CDATA[
Mage.Cookies.path = '<?php echo $this->getPath()?>';
Mage.Cookies.domain = '<?php echo $this->getDomain()?>';
//]]>
</script>
然后此代码引用Mage_Page_Block_Js_Cookie类中的getDomain()函数:
public function getDomain()
{
$domain = $this->getCookie()->getDomain();
if (!empty($domain[0]) && ($domain[0] !== '.')) {
$domain = '.'.$domain;
}
return $domain;
}
因此,如果我在系统配置中将Cookie域设置为“ www.abc.com”,则最终得到:
Mage.Cookies.domain = '.www.abc.com'
并在浏览器中找到“ www.abc.com”和“ .www.abc.com” Cookie,我想,“好吧,我将在系统配置中设置“ .abc.com”,并且始终以“ .abc.com'Cookies!” ...
但是没办法。现在,在我的HTML页面中,我总是得到“ .abc.com”,但是仍然错误地获得了“ www.abc.com” Cookie,并且没有登录。
我很困惑,我的客户开始认为我不如他想的那样好(我也开始认为...):(
你们中的一些人(和女孩)有什么暗示吗?
更新: 我见过有人将会话和cookie的问题与使用Varnish作为Magento的缓存有关。当我也使用Varnish时,如果禁用它,我会尝试解决该问题。