Ist es in Ordnung, wenn die erste Antwort mit AppCache (Symfony2) privat ist?

140

Ich versuche, http-Caching zu verwenden. In meinem Controller stelle ich eine Antwort wie folgt ein:

$response->setPublic();
$response->setMaxAge(120);
$response->setSharedMaxAge(120);
$response->setLastModified($lastModifiedAt);

Entwicklungsmodus

In der Entwicklungsumgebung ist die erste Antwort eine 200 mit folgenden Headern:

cache-control:max-age=120, public, s-maxage=120
last-modified:Wed, 29 Feb 2012 19:00:00 GMT

Für die nächsten 2 Minuten ist jede Antwort eine 304 mit folgenden Überschriften:

cache-control:max-age=120, public, s-maxage=120

Dies ist im Grunde das, was ich erwarte.

Prod-Modus

Im Prod-Modus sind die Antwortheader unterschiedlich. Beachten Sie, dass ich in app.php den Kernel in AppCache einbinde.

Die erste Antwort ist eine 200 mit folgenden Überschriften:

cache-control:must-revalidate, no-cache, private
last-modified:Thu, 01 Mar 2012 11:17:35 GMT

Es handelt sich also um eine private Antwort ohne Cache.

Jede nächste Anfrage ist so ziemlich das, was ich erwarten würde; a 304 mit folgenden Überschriften:

cache-control:max-age=120, public, s-maxage=120

Soll ich mir darüber Sorgen machen? Ist es ein erwartetes Verhalten?

Was passiert, wenn ich einen Lack- oder Akamai-Server davor stelle?

Ich habe ein bisschen debuggt und festgestellt, dass die Antwort aufgrund des zuletzt geänderten Headers privat ist. Der HttpCache-Kernel verwendet EsiResponseCacheStrategy , um die zwischengespeicherte Antwort zu aktualisieren ( HttpCache :: handle () -Methode).

if (HttpKernelInterface::MASTER_REQUEST === $type) {
    $this->esiCacheStrategy->update($response);
}

EsiResponseCacheStrategy wandelt eine Antwort in eine nicht zwischenspeicherbare Antwort um, wenn entweder Last-Response oder ETag ( EsiResponseCacheStrategy :: add () -Methode) verwendet wird:

if ($response->isValidateable()) {
    $this->cacheable = false;
} else {
    // ... 
}

Response :: isValidateable () gibt true zurück, wenn der Header Last-Response oder ETag vorhanden ist.

Dies führt zum Überschreiben des Cache-Control-Headers ( EsiResponseCacheStrategy :: update () -Methode):

if (!$this->cacheable) {
    $response->headers->set('Cache-Control', 'no-cache, must-revalidate');

    return;
}

Ich habe diese Frage in der Symfony2-Benutzergruppe gestellt, aber bisher keine Antwort erhalten: https://groups.google.com/d/topic/symfony2/6lpln11POq8/discussion

Aktualisieren.

Da ich keinen Zugriff mehr auf den Originalcode habe, habe ich versucht, das Szenario mit der neuesten Symfony-Standardversion zu reproduzieren .

Antwortheader sind jetzt konsistenter, scheinen aber immer noch falsch zu sein.

Sobald ich einen Last-ModifiedHeader für die Antwort gesetzt habe, hat die erste Antwort eines Browsers Folgendes:

Cache-Control:must-revalidate, no-cache, private

Die zweite Antwort hat eine Erwartung:

Cache-Control:max-age=120, public, s-maxage=120

Wenn ich das Senden von If-Modified-SinceHeadern vermeide, wird jede Anfrage zurückgegeben must-revalidate, no-cache, private.

Es spielt keine Rolle mehr, ob die Anfrage in prododer in der devUmgebung gestellt wurde.

Jakub Zalas
quelle
3
wenn ich den $ kernel = new AppCache ($ kernel) deaktiviere; es wird mir als öffentlich gezeigt. aber dann wird es immer mit einem Code 200 antworten ... ich benutze als Revery-Proxy-Nginx.
Michael
sind deine app.phpund app_dev.phpdie gleichen? (ignoriert Debug und env)
Florian Klein
1
Ich habe keinen Zugriff mehr auf dieses Projekt und kann dies daher nicht bestätigen. Ich erinnere mich, dass Controller Standard-Controller mit aktiviertem AppCache waren.
Jakub Zalas
1
@Florian Ich habe versucht, das Problem zu reproduzieren, und ich habe ein etwas anderes Verhalten mit der neuesten Symfony-Version (siehe Update).
Jakub Zalas
2
Würden Sie debug=>truegetOptions () in AppCache festlegen, damit Sie den X-Symfony-CacheHeader erhalten?
denkiryokuhatsuden

Antworten:

9

Ich habe das gleiche Problem konfrontiert. Ich musste 'öffentliche' Header meiner CDN liefern. Wenn das Gateway-Caching im Prod-Modus aktiviert ist, wird standardmäßig 200 OK mit privat zurückgegeben. Der Nocache muss die Header validieren.

Ich habe das Problem auf diese Weise gelöst.

Bevor ich in app.php eine Antwort an den Benutzer sende ($ reply-> send), habe ich den Cache-Steuerungsheader auf leer überschrieben und die Cache-Header auf public und max age (ein gewisser Wert) gesetzt.

// Code-Snippet aus app.php

    $response = $kernel->handle($request);
    $response->headers->set('Cache-Control', '');
    $response->setPublic();
    $response->setMaxAge(86400);
    $response->send();        
Srikanthsatturi
quelle
Haben Sie private Antworten erhalten, obwohl diese in einem Controller öffentlich gemacht wurden?
Jakub Zalas
Ja, wenn ich das Gateway-Caching aktiviere und es im Prod-Modus ausführe. Ich brauchte die obige Lösung für statische Inhalte.
Srikanthsatturi
-4

Das Verhalten, das Sie erleben, ist beabsichtigt. Symfony2-Dokumente beschreiben explizit die Situationen, in denen privat und öffentlich verwendet werden, wobei standardmäßig privat ist .

Udan
quelle
Dies ist leider nicht mein Fall.
Jakub Zalas