Sto scoprendo che ogni volta che riavvio Varnish sul mio server, sto perdendo le sessioni per i miei utenti.
Questo è il turno che fa perdere ai miei clienti i loro carrelli della spesa.
È questo comportamento normale per Varnish o è colpa mia VCL? Sembrerebbe che non lo sia
Ulteriori informazioni
Su ulteriori indagini, sembra che questo problema sia correlato al numero 725 su GitHub.
La mia installazione di Magento è la versione 1.9.1.0. Va anche detto che il mio intero frontend viene eseguito in https. Sto usando Pound davanti a Varnish per terminare SSL.
Sembra che il comportamento predefinito di Magento in questa versione sia quello di creare un cookie frontend secondario, in genere chiamato "frontend_cid", nel tentativo di verificare gli attacchi MITM.
Sembra che il file VCL generato da Turpentine non stia trasmettendo questo cookie, causando sessioni non valide.
Qualcuno può spiegare come il file VCL trasmette i cookie che Magento invia al Cliente?
L'ho ridotto a Vernice non generando i cookie richiesti.
A partire da Magento 1.9.1.0, è stato introdotto un cookie "frontend_cid" per bloccare gli attacchi MITM.
Questo può essere trovato nella Mage_Core_Model_Session_Abstract_Varien
classe, alla riga 135
if (Mage::app()->getFrontController()->getRequest()->isSecure() && empty($cookieParams['secure'])) {
// secure cookie check to prevent MITM attack
$secureCookieName = $sessionName . '_cid';
if (isset($_SESSION[self::SECURE_COOKIE_CHECK_KEY])
&& $_SESSION[self::SECURE_COOKIE_CHECK_KEY] !== md5($cookie->get($secureCookieName))
) {
session_regenerate_id(false);
$sessionHosts = $this->getSessionHosts();
$currentCookieDomain = $cookie->getDomain();
foreach (array_keys($sessionHosts) as $host) {
// Delete cookies with the same name for parent domains
if (strpos($currentCookieDomain, $host) > 0) {
$cookie->delete($this->getSessionName(), null, $host);
}
}
$_SESSION = array();
}
if (!isset($_SESSION[self::SECURE_COOKIE_CHECK_KEY])) {
$checkId = Mage::helper('core')->getRandomString(16);
$cookie->set($secureCookieName, $checkId, null, null, null, true);
$_SESSION[self::SECURE_COOKIE_CHECK_KEY] = md5($checkId);
}
}
Al fine di fornire connessioni sicure per i clienti, Varnish deve generare un cookie "frontend", che Magento utilizzerà successivamente per identificare quel particolare cliente. Finora sembra farlo bene. Tuttavia, sembra che a partire da Magento 1.9.1.0, ora debba anche generare il cookie "frontend_cid".
Varnish deve farlo perché, memorizzando nella cache la risposta, memorizza anche nella cache l'intestazione della risposta, che contiene i cookie di "frontend".
Pertanto, per impostazione predefinita, Varnish elimina tutti i cookie con cui il backend risponde quando gestisce le condizioni di "ricerca" o "passaggio". Lo fa per impedire a più utenti di essere emessi con lo stesso cookie frontend nella cache (ciò comprometterebbe le sessioni delle persone).
Ogni volta che la vernice gestisce la richiesta con 'pipe', Magento è in grado di creare i cookie richiesti e collegarli al browser degli utenti. Ciò comporta la mancata convalida iniziale del sistema, ma fornisce quindi una nuova sessione all'utente. Questo sintomo si manifesta come perdita del carrello o incapacità di aggiungere prodotti al carrello.
Il VCL di trementina "convoglia" qualsiasi richiesta che NON sia di tipo GET o HEAD come visto da questo codice nella vcl_recv
funzione:
// We only deal with GET and HEAD by default
// we test this here instead of inside the url base regex section
// so we can disable caching for the entire site if needed
if (!true || req.http.Authorization ||
req.request !~ "^(GET|HEAD)$" ||
req.http.Cookie ~ "varnish_bypass=1") {
return (pipe);
}
Pertanto, il sintomo è più evidente quando l'utente tenta di aggiungere un articolo al carrello o tenta di effettuare il checkout per la prima volta.
Come risolvere?
Credo che la soluzione a questo problema sia che il VCL di trementina crei anche un cookie "frontend_cid" per i visitatori in arrivo, e quindi il modulo trementina aggiunga quel cookie alla sessione corrente come fa ora per il cookie "frontend".
Quindi ... come lo implementiamo?
Avvertenza: potrei sbagliarmi, sono molto nuovo su Varnish, ma ho passato molte ore su questo ora e questo è quello che vedo, chiunque supporto in questo momento sarebbe molto apprezzato.
AGGIORNAMENTO FINALE E LA MIA SCELTA SCELTA - 2015 10 30
È impossibile creare un cookie "frontend_cid" in vernice poiché il cookie viene creato in modo casuale sul server da Magento e memorizzato come hash MD5 nella sessione dei clienti. Questo ti impedisce di creare esternamente al di fuori della sessione dei clienti.
La migliore soluzione che ho trovato su questo problema è invece di sovrascrivere il modo in cui Magento gestisce le sessioni dei clienti.
Attualmente Magento gestisce sessioni non valide come questa:
IF
The requested session by the customer is flagged as invalid
THEN
Stop processing request
Redirect to the appropriate page
La mia nuova logica è la seguente:
IF
The requested session by the customer is flagged as invalid
THEN
Create a new session
Complete the requested task
Redirect to the appropriate page
Il mio nuovo approccio consente a verniciato di gestire la risposta dei clienti anche alla prima visita. Non è così che funziona l'ultima implementazione della trementina.
My Issue, Issue # 829 - / nexcess / magento-trementina / issues / 829 su GitHub. Una copia del mio VCL può essere trovata qui.
Il mio problema su GitHub è stato chiuso in quanto è un duplicato di un problema molto più vecchio trovato qui: