2017-02-02 2 views
1

Ich habe einen Block, der auf einem ziemlich flockigen Third-Party-Service angewiesen ist, um Daten zu rendern, wenn es auf ein Problem stößt. Ich möchte eine Fehlermeldung anzeigen, anstatt eine Ausnahme auszulösen und die Seite nicht zu rendern.Concrete5 (5.7) - Cache nicht Seite oder aktueller Block bei Block Fehler

Einfach genug zu tun, bis Sie zum Block/Seite Caching kommen. Die Daten haben eine lange Lebensdauer. Wenn sie gefunden werden, ist es in Ordnung, alles zwischenzuspeichern. Wenn dies nicht der Fall ist, wird die Seite mit der Fehlermeldung zwischengespeichert. Daher muss ich dem CMS mitteilen, dass die Ausgabe des Blocks oder der Seite nicht im Cache gespeichert werden soll.

Beispiel-Code (im Block-Controller):

public function view() { 
    try { 
     $this->set ('data', $this->getData()); 

    } catch (\Exception $e) { 
     \Log::addError ('Blockname Error: '.$e->getMessage(), [$e]); 
     $this->render ('error'); 
    } 
} 

Im catch-Block habe ich versucht, sowohl $this->btCacheBlockOutput = true; und \Cache::disableAll(); aber weder funktioniert. Gibt es eine Möglichkeit, C5 mitzuteilen, dass bei der aktuellen Anfrage nichts zwischengespeichert wird?

Antwort

0

Die BlockController im konkreten Ordner diese geschützten Variablen als Standard hat:

protected $btCacheBlockRecord = true; 
protected $btCacheBlockOutput = false; 
protected $btCacheBlockOutputOnPost = false; 
protected $btCacheBlockOutputForRegisteredUsers = false; 

Also, wenn Sie alle diese auf Ihrem Block controller.php auf false gesetzt ist, sollte es nicht dem Block zwischenspeichern.

class Controller extends BlockController 
{ 
    protected $btCacheBlockRecord = false; 
    protected $btCacheBlockOutput = false; 
    protected $btCacheBlockOutputOnPost = false; 
    protected $btCacheBlockOutputForRegisteredUsers = false; 
    public function view(){ 
    ..... 

Dies wird das Caching des Blockes (auch wenn die Dritte Verbindung erfolgreich) deaktivieren. Eine andere Lösung besteht darin, die von der dritten Partei in der Datenbank empfangenen Daten zu speichern (z. B. als JSON-Zeichenfolge) und die Daten aus der Datenbank zu laden, wenn die Verbindung des Drittanbieters fehlschlägt ... wenn die Verbindung des Drittanbieters erfolgreich ist , können Sie den Datensatz in der Datenbank aktualisieren.

Abhängig von der Antwort des Drittdienstes können Sie die Bedingungen festlegen. Beispiel:

//service returns on OK: 
//array('status' => 'ok') 
//service returns on NOT OK: 
//array('status' => 'nok') 

public function view() { 
    $data = $this->getData(); 
    if($data['status'] == 'ok'){ 
     //save data to database in a config value using concrete Config class 
     $configDatabase = \Core::make('config/database'); 
     $configDatabase->save('thirdpartyanswer', $data); 
     $this->set('data', $data); 
    }else{ 
     //getData function returned error or nok status 
     //get data from concrete Config class 
     $configDatabase = \Core::make('config/database'); 
     if($configDatabase->get('thirdpartyanswer')) != ''){ 
      //set data as "old" data from config 
      $this->set('data', $configDatabase->get('thirdpartyanswer')); 
     }else{ 
      //no data in config -> set error and nothing else 
      $this->set('error', 'An error occured contacting the third party'); 
     } 
    } 
} 

(Der obige Code wurde nicht getestet)
Weitere Informationen zur Speicherung von Konfigurationswerten:
https://documentation.concrete5.org/developers/packages/storing-configuration-values

* Edit *

Eine dritte Option ist, auszuspülen der Cache für diese bestimmte Seite, wenn der Aufruf fehlschlägt.

An der Spitze Ihres blockcontroller:

use \Concrete\Core\Cache\Page\PageCache; 
use Page; 

In der 'wenn', wenn der Aufruf an die API fehlschlägt:

$currentPage = Page::getCurrentPage(); 
$cache = PageCache::getLibrary(); 
$cache->purge($currentPage); 

Gefunden bei: https://www.concrete5.org/community/forums/5-7-discussion/programmatically-expiring-pages-from-cache

+0

Danke, aber das doesn Beantworte die Frage nicht. Der Block wird auf Seiten mit hohem Datenaufkommen verwendet, bei denen das vollständige Zwischenspeichern von Seiten wirklich erforderlich ist. Ich speichere bereits die Daten im "teuren" (Datenträger-) Cache, was perfekt dafür ist, aber das Seiten-Caching-Problem nicht behebt. –

+0

Ich habe meine Antwort bearbeitet, siehe 'dritte' Option. Ich habe getestet, ob die Seite noch geladen ist, also ist der Code gültig. – Jozzeh

+0

Wenn das Löschen der Seite aus dem Cache verhindert, dass die aktuell gerenderte Ausgabe zwischengespeichert wird, ist das ein guter Anfang, aber bei einem schnellen Test sehe ich immer noch die alte Blockausgabe. Vermutlich würde dies vom Blockausgabe-Cache kommen, der Aufruf der RefreshBlockOutputCache-Methode des relevanten Blockobjekts in der Fehlerbehandlung scheint nicht zu helfen. Vielleicht hilft das manuelle Auffüllen des cacheSettings-Objekts des Blocks an dieser Stelle, ich muss später spielen, wenn ich Zeit habe. –