ini akan lama ...
Saya mendapat kasus buruk kegagalan login yang tidak menentu, karena manajemen cookie yang salah. Pertama-tama, saya mengelola toko tertutup (B2B) di mana pelanggan harus masuk sebelum mereka dapat melihat katalog. Setiap akses yang tidak terdaftar akan diarahkan ke halaman login, tetapi sesekali pelanggan tidak dapat login bahkan jika nama pengguna dan kata sandi benar. Saya mengatakan 'nama pengguna' karena saya menggunakan ekstensi Diglin_Username dan plugin StoreRestricition untuk mencapai perilaku yang diinginkan. Apa yang terjadi adalah bahwa kadang-kadang saya menemukan dua set cookie berbeda yang ditinggalkan oleh Magento, dan mereka merujuk pada dua domain yang berbeda (.www.abc.com dan .abc.com misalnya).
Setelah membaca artikel ini dari Alan Storm pada instantiasi awal sesi, dan menemukan cookie PHPSESSID yang ditakuti di browser saya, saya menyelidiki secara mendalam masalah ini.
Apa yang saya temukan adalah bermuka dua. Pertama saya meletakkan panggilan Mage :: Log () di fungsi start () di kelas Mage_Core_Model_Session_Abstract_Varien untuk mencatat berbagai upaya yang dilakukan oleh Magento untuk memulai sesi baru dan memperhatikan bahwa mengikuti Mage :: run () yang pertama memanggil preDispatch () , dispatch () dan metode postDispatch () dari kelas Mage_Core_Controller_Front_Action dipanggil dalam urutan yang biasa tetapi tampaknya ketika postDispatch () dijalankan tidak dapat menemukan sesi dimulai dengan preDispatch () dan melanjutkan untuk membuat sesi baru. Untuk hal ini saya menemukan perbedaan dalam kode antara versi Magento 1.7.x dan 1.8.x dan saya pikir itu mungkin bisa mengatasi masalah ini:
Magento 1.7.x - Mage_Core_Model_Session_Abstract_Varien kelas:
public function start($sessionName=null)
{
if (isset($_SESSION)) {
return $this;
}
.
.
}
Magento 1.8.x - Mage_Core_Model_Session_Abstract_Varien kelas:
public function start($sessionName=null)
{
if (isset($_SESSION) && !$this->getSkipEmptySessionCheck()) {
return $this;
}
.
.
}
Saya tidak bisa menemukan tempat untuk mengatur properti SkipEmptySessionCheck, jadi saya akhirnya menambal kelas Mage_Core_Controller_Front_Action dengan cara ini:
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;
}
untuk memiliki postDispatch () tidak memanggil Mage :: getSingleton ('core / session') (yang akan membuat sesi baru) jika tidak dapat menemukan sesi sudah dimulai. Selama cookie PHPSESSID dan semua selesai, saya pikir ...
Tapi tidak demikian. Sekarang saya menyingkirkan cookie PHPSESSID tetapi masih kebagian dua cookie yang berbeda (tidak menentu) yang disimpan di browser. Hanya menghapus cookie yang salah, saya dapat berhasil login, atau saya diarahkan ke halaman login bahkan tanpa pesan. Saya mencoba untuk menyatakan domain cookie secara eksplisit dalam konfigurasi sistem tetapi ini tidak menyelesaikan masalah.
Jauh di dalam basis kode lagi, dan saya menemukan bahwa di berbagai tempat ketika Magento menetapkan cookie, diperlukan domain untuk digunakan dari fungsi getDomain () di kelas Mage_Core_Model_Cookie:
public function getDomain()
{
$domain = $this->getConfigDomain();
if (empty($domain)) {
$domain = $this->_getRequest()->getHttpHost();
}
return $domain;
}
Sekarang, jika Anda melihat halaman yang Anda dapatkan dari Magento di browser Anda, Anda dapat menemukannya di bagian 'head' seperti ini:
<script type="text/javascript">
//<![CDATA[
Mage.Cookies.path = '/';
Mage.Cookies.domain = '.www.abc.com';
//]]>
</script>
Baris-baris ini berasal dari app / desain / frontend / base / default / template / halaman / js / cookie.phtml:
<script type="text/javascript">
//<![CDATA[
Mage.Cookies.path = '<?php echo $this->getPath()?>';
Mage.Cookies.domain = '<?php echo $this->getDomain()?>';
//]]>
</script>
dan pada gilirannya, kode ini merujuk fungsi getDomain () di kelas Mage_Page_Block_Js_Cookie:
public function getDomain()
{
$domain = $this->getCookie()->getDomain();
if (!empty($domain[0]) && ($domain[0] !== '.')) {
$domain = '.'.$domain;
}
return $domain;
}
Jadi, jika saya menetapkan domain cookie dalam konfigurasi sistem sebagai, misalnya, 'www.abc.com', saya berakhir dengan:
Mage.Cookies.domain = '.www.abc.com'
dan menemukan di cookie saya cookie 'www.abc.com' dan '.www.abc.com' saya pikir, "ok, saya akan menetapkan '.abc.com' di konfigurasi sistem dan akan selalu berakhir dengan ' cookie .abc.com !! "...
Tapi tidak mungkin. Sekarang di halaman HTML saya, saya selalu mendapatkan '.abc.com' tetapi meskipun demikian saya masih tidak menentu mendapatkan cookie 'www.abc.com' dan tanpa login.
Saya bingung, dan pelanggan saya mulai berpikir saya tidak sebagus yang dia kira (saya juga mulai berpikir ...) :(
Apakah beberapa dari kalian (dan cewek-cewek) punya beberapa petunjuk?
PEMBARUAN: Saya telah melihat seseorang mengaitkan masalah dengan sesi dan cookie dengan penggunaan Varnish sebagai cache untuk Magento. Karena saya menggunakan Varnish juga saya akan mencoba jika menonaktifkannya masalah ini dapat diselesaikan.